/* The original version of this program can be found at http://damb.dk */
#include <windows.h>
#include <commctrl.h>
#include <string>
#include <sstream>
enum WindowsId
{
FirstEditId = 256,
FirstUpDownId,
SecondEditId,
SecondUpDownId,
ResultListBoxId,
SubRadioId,
AddRadioId,
HexCheckId,
ButtonId,
GroupBoxId,
ProgressCtrlId
};
enum TimerId
{
ProgressTimer = 1024
};
template <typename T>
std::string ToString(T aValue)
{
std::stringstream ss;
ss << aValue;
return ss.str();
}
template <typename T>
std::string ToStringHex(T aValue)
{
std::stringstream ss;
ss << std::hex << aValue;
return ss.str();
}
HINSTANCE InstanceHandle;
bool TimerRunning;
int TimerIdx;
void AddListText(HWND aMainWnd, const char *aMsg)
{
static int MaxWidth;
HWND List = GetDlgItem(aMainWnd, ResultListBoxId);
int idx = SendMessage(List, LB_ADDSTRING, 0, (LPARAM )aMsg);
SendMessage(List, LB_SETCARETINDEX, idx, 0);
HDC dc = GetDC(List);
HFONT Font = (HFONT )SendMessage(aMainWnd, WM_GETFONT, 0, 0);
HFONT OldFont = (HFONT )SelectObject(dc, Font);
SIZE TextSize;
GetTextExtentPoint32(dc, aMsg, strlen(aMsg), &TextSize);
TextSize.cx += 10;
if(TextSize.cx > MaxWidth)
{
MaxWidth = TextSize.cx;
SendMessage(List, LB_SETHORIZONTALEXTENT, MaxWidth, 0);
}
SelectObject(dc, OldFont);
ReleaseDC(List, dc);
}
void OnSize(HWND aMainWnd, int aWidth, int aHeight)
{
HWND Control;
Control = GetDlgItem(aMainWnd, ResultListBoxId);
MoveWindow(Control, 5, 60, aWidth - 10, aHeight - 170, FALSE);
Control = GetDlgItem(aMainWnd, AddRadioId);
MoveWindow(Control, 10, aHeight - 90, 50, 14, FALSE);
Control = GetDlgItem(aMainWnd, SubRadioId);
MoveWindow(Control, 60, aHeight - 90, 50, 14, FALSE);
Control = GetDlgItem(aMainWnd, HexCheckId);
MoveWindow(Control, 120, aHeight - 90, 50, 14, FALSE);
Control = GetDlgItem(aMainWnd, GroupBoxId);
MoveWindow(Control, 5, aHeight - 110, 110, 40, FALSE);
Control = GetDlgItem(aMainWnd, ButtonId);
MoveWindow(Control, 5, aHeight - 62, 75, 25, FALSE);
Control = GetDlgItem(aMainWnd, ProgressCtrlId);
MoveWindow(Control, 5, aHeight - 32, aWidth - 10, 25, FALSE);
}
LRESULT CALLBACK DialogProc(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch(msg)
{
case WM_CREATE:
CreateWindowEx(WS_EX_CLIENTEDGE,
"EDIT",
"",
WS_CHILD | WS_VISIBLE | ES_NUMBER | WS_TABSTOP | WS_GROUP,
5, 5, 120, 20,
hwndDlg,
(HMENU)(FirstEditId),
InstanceHandle,
0);
CreateWindow(UPDOWN_CLASS,
"Spin1",
UDS_AUTOBUDDY | UDS_ALIGNRIGHT | UDS_SETBUDDYINT | WS_CHILD | WS_VISIBLE | UDS_ARROWKEYS,
105, 5, 20, 20,
hwndDlg,
(HMENU )FirstUpDownId,
InstanceHandle,
0);
SendDlgItemMessage(hwndDlg, FirstUpDownId, UDM_SETRANGE, 0, MAKELONG(100, -100));
CreateWindowEx(WS_EX_CLIENTEDGE,
"EDIT",
"",
WS_CHILD | WS_VISIBLE | ES_NUMBER | WS_TABSTOP,
5, 35, 120, 20,
hwndDlg,
(HMENU)(SecondEditId),
InstanceHandle,
0);
CreateWindow(UPDOWN_CLASS,
"Spin2",
UDS_AUTOBUDDY | UDS_ALIGNRIGHT | UDS_SETBUDDYINT | WS_CHILD | WS_VISIBLE | UDS_ARROWKEYS,
105, 35, 20, 20,
hwndDlg,
(HMENU )SecondUpDownId,
InstanceHandle,
0);
SendDlgItemMessage(hwndDlg, SecondUpDownId, UDM_SETRANGE, 0, MAKELONG(100, -100));
CreateWindowEx(WS_EX_CLIENTEDGE,
"LISTBOX",
"0",
WS_CHILD | WS_VISIBLE | WS_TABSTOP | WS_VSCROLL | WS_HSCROLL,
5, 65, 120, 80,
hwndDlg,
(HMENU )ResultListBoxId,
InstanceHandle,
0);
CreateWindow("BUTTON",
"Add",
WS_CHILD | WS_VISIBLE | WS_TABSTOP | BS_AUTORADIOBUTTON,
10, 155, 50, 14,
hwndDlg,
(HMENU )AddRadioId,
InstanceHandle,
0);
CreateWindow("BUTTON",
"Sub",
WS_CHILD | WS_VISIBLE | WS_TABSTOP | BS_AUTORADIOBUTTON,
65, 155, 50, 14,
hwndDlg,
(HMENU )SubRadioId,
InstanceHandle,
0);
CreateWindow("BUTTON",
"Hex",
WS_CHILD | WS_VISIBLE | WS_TABSTOP | BS_AUTOCHECKBOX,
120, 155, 50, 14,
hwndDlg,
(HMENU )HexCheckId,
InstanceHandle,
0);
CreateWindow("BUTTON",
"Calculate",
WS_CHILD | WS_VISIBLE | WS_TABSTOP,
5, 180, 120, 30,
hwndDlg,
(HMENU )ButtonId,
InstanceHandle,
0);
CreateWindow("BUTTON",
"Action",
WS_CHILD | WS_VISIBLE | BS_GROUPBOX,
5, 135, 120, 40,
hwndDlg,
(HMENU )GroupBoxId,
InstanceHandle,
0);
CreateWindow(PROGRESS_CLASS,
"",
WS_CHILD | WS_VISIBLE | PBS_SMOOTH,
5, 100, 100, 20,
hwndDlg,
(HMENU )ProgressCtrlId,
InstanceHandle,
0);
SendDlgItemMessage(hwndDlg, ProgressCtrlId, PBM_SETRANGE, 0, MAKELPARAM(0, 50));
CheckDlgButton(hwndDlg, AddRadioId, BST_CHECKED);
break;
case WM_GETMINMAXINFO:
{
MINMAXINFO *MinMaxInfo = (MINMAXINFO *)lParam;
MinMaxInfo->ptMinTrackSize.x = 140;
MinMaxInfo->ptMinTrackSize.y = 250;
break;
}
case WM_SIZE:
OnSize(hwndDlg, LOWORD(lParam), HIWORD(lParam));
break;
case WM_COMMAND:
if(HIWORD(wParam) == BN_CLICKED && LOWORD(wParam) == ButtonId)
{
if(!TimerRunning)
{
TimerIdx = 1;
TimerRunning = true;
SetTimer(hwndDlg, ProgressTimer, 100, 0);
SendDlgItemMessage(hwndDlg, ProgressCtrlId, PBM_SETPOS, TimerIdx, 0);
}
}
break;
case WM_TIMER:
TimerIdx++;
SendDlgItemMessage(hwndDlg, ProgressCtrlId, PBM_SETPOS, TimerIdx, 0);
if(TimerIdx > 50)
{
KillTimer(hwndDlg, ProgressTimer);
TimerRunning = false;
int First = GetDlgItemInt(hwndDlg, FirstEditId, 0, FALSE);
int Second = GetDlgItemInt(hwndDlg, SecondEditId, 0, FALSE);
int Result;
std::string ResultString;
std::string Op;
if(IsDlgButtonChecked(hwndDlg, AddRadioId))
{
Result = First + Second;
Op = " + ";
}
else
{
ResultString = ToString(First) + " - " + ToString(Second) + " = " + ToString(Result);
Op = " - ";
}
ResultString = ToString(First) + Op + ToString(Second) + " = ";
bool DoHex = SendDlgItemMessage(hwndDlg, HexCheckId, BM_GETCHECK, 0, 0) == BST_CHECKED;
if(DoHex)
ResultString += std::string("0x") + ToStringHex(Result);
else
ResultString += ToString(Result);
AddListText(hwndDlg, ResultString.c_str());
break;
}
}
return DefWindowProc(hwndDlg, msg, wParam, lParam);
}
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR lpCmdLine, INT nCmdShow)
{
InstanceHandle = hInstance;
InitCommonControls();
WNDCLASS wc;
memset(&wc, 0, sizeof(WNDCLASS));
wc.style = CS_HREDRAW | CS_VREDRAW | CS_DBLCLKS;
wc.lpfnWndProc = DialogProc;
wc.hInstance = InstanceHandle;
wc.hbrBackground = (HBRUSH )(COLOR_BTNFACE + 1);
wc.lpszClassName = "WhateverClass";
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
if(!RegisterClass(&wc))
return FALSE;
HWND WindowHandle = CreateWindow("WhateverClass",
"Calc", // Caption text
WS_MINIMIZEBOX | WS_VISIBLE | WS_MAXIMIZEBOX |
WS_CAPTION | WS_BORDER | WS_SYSMENU | WS_THICKFRAME,
100, 100, 180, 245, // Position
NULL,
NULL,
InstanceHandle,
0);
MSG Msg;
while(GetMessage(&Msg, WindowHandle, 0, 0xFFFF) > 0)
{
if(!IsDialogMessage(WindowHandle, &Msg))
{
TranslateMessage(&Msg);
DispatchMessage(&Msg);
}
}
return 0;
}