Up-Down control taller than buddy - c

Plain C, winapi app.
On a dialog box created from a resource script it fits perfectly, but created with CreateWindowEx the Up-Down control is taller than the buddy window (edit control) by one pixel on either side.
It's not that big of a deal, but it's pretty nagging. I tried everything I could think of and couldn't get it fixed, any help is appreciated.
Here's the code:
#include <Windows.h>
#include <Commctrl.h>
#include <stdio.h>
#define print(...) sprintf(dbg, __VA_ARGS__);\
WriteConsoleA(h_con_out, dbg, strlen(dbg), NULL, NULL)
TCHAR *app_name = TEXT("ud");
HANDLE h_con_out;
char dbg[80];
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow){
HWND hwnd;
MSG msg;
WNDCLASSEX wcx;
INITCOMMONCONTROLSEX icx = {sizeof(icx), ICC_STANDARD_CLASSES | ICC_UPDOWN_CLASS};
AllocConsole();
h_con_out = GetStdHandle(STD_OUTPUT_HANDLE);
memset(&wcx, 0, sizeof(wcx));
wcx.cbSize = sizeof(wcx);
wcx.lpfnWndProc = WndProc;
wcx.hInstance = hInstance;
wcx.hCursor = LoadCursor(NULL, IDC_ARROW);
wcx.hbrBackground = (HBRUSH) (COLOR_BTNFACE + 1);
wcx.lpszClassName = app_name;
if(!RegisterClassEx(&wcx)){
MessageBox(NULL, TEXT("This program requires Windows 2000!"), app_name, MB_ICONERROR);
return 0;
}
InitCommonControlsEx(&icx);
hwnd = CreateWindowEx(
0, app_name, app_name,
WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX,
CW_USEDEFAULT, CW_USEDEFAULT, 200, 100,
NULL, NULL, hInstance, NULL
);
ShowWindow(hwnd, iCmdShow);
UpdateWindow(hwnd);
while((GetMessage(&msg, NULL, 0, 0)) != 0){
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return msg.wParam;
}
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam){
static HWND hEd, hUd;
switch(msg){
case WM_CREATE:
hEd = CreateWindowEx(
WS_EX_CLIENTEDGE, WC_EDIT, NULL,
WS_VISIBLE | WS_CHILD | WS_BORDER |
ES_RIGHT | ES_NUMBER,
5, 5, 52, 23,
hwnd, NULL, ((LPCREATESTRUCT) lParam)->hInstance, NULL
);
hUd = CreateWindowEx(
0, UPDOWN_CLASS, NULL,
WS_VISIBLE | WS_CHILD |
UDS_ALIGNRIGHT | UDS_ARROWKEYS | UDS_NOTHOUSANDS | UDS_AUTOBUDDY | UDS_HOTTRACK | UDS_SETBUDDYINT | UDS_AUTOBUDDY,
0, 0, 0, 0,
hwnd, NULL, ((LPCREATESTRUCT) lParam)->hInstance, NULL
);
SendMessage(hUd, UDM_SETRANGE, 0, 10 | 1 << 16);
return 0;
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hwnd, msg, wParam, lParam);
}

Remove WS_BORDER from the edit controls style.

Related

How to call another screen in this code below

Good night, I would like some help with this code below, I have to do an exercise that calls another registration screen, the first screen I managed to assemble, make the buttons work too, but I don't find a practical example on the internet to be able to call this one another screen, I've tried in several ways and without success, I would like some help so to be able to call another screen in this code below. I have to call this other screen there on the Register button, you can see that I've already tried and nothing happens.
#define UNICODE
#define _UNICODE
#include <windows.h>
#include <tchar.h>
const TCHAR CLSNAME[] = TEXT("helloworldWClass");
LRESULT CALLBACK winproc(HWND hwnd, UINT wm, WPARAM wp, LPARAM lp);
void addControls(HWND);
int WINAPI WinMain(HINSTANCE hInst, HINSTANCE hInstPrev, PSTR cmdline, int cmdshow)
{
//return MessageBox(NULL, "hello, world", "caption", 0);
WNDCLASSEX wc = { };
MSG msg;
HWND hwnd;
wc.cbSize = sizeof (wc);
wc.style = 0;
wc.lpfnWndProc = winproc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInst;
wc.hIcon = LoadIcon (NULL, IDI_APPLICATION);
wc.hCursor = LoadCursor (NULL, IDC_ARROW);
//wc.hbrBackground = (HBRUSH) GetStockObject (WHITE_BRUSH);
wc.lpszMenuName = NULL;
wc.lpszClassName = CLSNAME;
wc.hIconSm = LoadIcon (NULL, IDI_APPLICATION);
if (!RegisterClassEx(&wc)) {
MessageBox(NULL, TEXT("Could not register window class"),
NULL, MB_ICONERROR);
return 0;
}
hwnd = CreateWindowEx(WS_EX_LEFT,
CLSNAME,
_T("Covid-19"),
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
CW_USEDEFAULT,
CW_USEDEFAULT,
NULL,
NULL,
hInst,
NULL);
if (!hwnd) {
MessageBox(NULL, TEXT("Could not create window"), NULL, MB_ICONERROR);
return 0;
}
ShowWindow(hwnd, cmdshow);
UpdateWindow(hwnd);
while (GetMessage(&msg, NULL, 0, 0)) {
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return msg.wParam;
}
void addControls(HWND hwnd) {
CreateWindowW(L"Static", L"Login", WS_CHILD | WS_VISIBLE, 600, 0, 100, 18, hwnd, NULL, NULL, NULL);
CreateWindowW(L"Edit", L"", WS_CHILD | WS_VISIBLE, 600, 40, 100, 18, hwnd, NULL, NULL, NULL);
CreateWindowW(L"Static", L"Senha", WS_CHILD | WS_VISIBLE, 600, 80, 100, 18, hwnd, NULL, NULL, NULL);
CreateWindowW(L"Edit", L"", WS_CHILD | WS_VISIBLE, 600, 120, 100, 18, hwnd, NULL, NULL, NULL);
CreateWindowW(L"Button", L"Login", WS_CHILD | WS_VISIBLE, 600, 160, 100, 18, hwnd, (HMENU) 1, NULL, NULL);
CreateWindowW(L"Button", L"Cadastrar", WS_CHILD | WS_VISIBLE, 600, 200, 100, 18, hwnd, (HMENU) 2, NULL, NULL);
}
LRESULT CALLBACK winproc(HWND hwnd, UINT wm, WPARAM wp, LPARAM lp) {
HWND hwndCadastrar;
switch (wm) {
case WM_CREATE:
addControls(hwnd);
break;
case WM_CLOSE:
DestroyWindow(hwnd);
break;
case WM_COMMAND:
if (LOWORD(wp) == 1) {
hwndCadastrar = CreateWindowEx(WS_EX_LEFT,
CLSNAME,
_T("Covid-19 - Cadastrar - Paciente"),
WS_CHILDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
CW_USEDEFAULT,
CW_USEDEFAULT,
NULL,
NULL,
hwnd,
NULL);
ShowWindow(hwndCadastrar, SW_SHOW);
SetForegroundWindow(hwndCadastrar);
SetFocus(hwndCadastrar);
Window(hwnd);
MessageBox(0, (LPCWSTR)L"Login Efetuado Com Sucesso", (LPCWSTR)L"Login", 0);
} else if (LOWORD(wp) == 2) {
MessageBox(0, (LPCWSTR)L"Cadastro Efetuado Com Sucesso", (LPCWSTR)L"Cadastrar", 0);
}
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return DefWindowProc(hwnd, wm, wp, lp);
}
}
The child window failed to create.
You cannot pass a HWND to a HINSTANCE parameter.(argument of type HWND is incompatible with parameter of type HINSTANCE)
You cannot create a top-level child window(ERROR_TLW_WITH_WSCHILD).
CW_USEDEFAULT is valid only for overlapped windows; if CW_USEDEFAULT is specified for a pop-up or child window, the nWidth and nHeight parameter are set to zero.
If you want to see the child window caption, add WS_CAPTION.
Finally, the code looks like this:
hwndCadastrar = CreateWindowEx(WS_EX_LEFT,
CLSNAME,
_T("Covid-19 - Cadastrar - Paciente"),
WS_CAPTION |WS_CHILDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
1000,
1000,
hwnd,
NULL,
GetModuleHandle(NULL),
NULL);
For more information about child windows, see Creating, Enumerating, and Sizing Child Windows

winapi full screen leaves 3 tickles

here is a code I found here :
https://www.codeproject.com/Questions/108400/How-to-Set-Win32-Application-to-Full-Screen-C
. I had a little problem with it. In part 1 it queries the window style and then in the second 2 part it defines styles that we will remove in part 3. then in part 4 leaves three butts on two sides and bottom. what can i do?
//move to full screen
//1
DWORD dwStyle = ::GetWindowLong(hwnd, GWL_STYLE);
//2
DWORD dwRemove = WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX | WS_MAXIMIZEBOX;
//3
DWORD dwNewStyle = dwStyle & ~dwRemove;
::SetWindowLong(hwnd, GWL_STYLE, dwNewStyle);
//4
::SetWindowPos(hwnd, NULL, 0, 0, ::GetDeviceCaps(hdc, HORZRES), ::GetDeviceCaps(hdc, VERTRES),SWP_FRAMECHANGED);
Raymond Chen gave the correct way to do this in his blog: How do I switch a window between normal and fullscreen?:
Here is the sample that you can refer to :
#include <Windows.h>
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
WINDOWPLACEMENT g_wpPrev = { sizeof(g_wpPrev) };
void setFullWindow(HWND hwnd)
{
DWORD dwStyle = GetWindowLong(hwnd, GWL_STYLE);
if (dwStyle & WS_OVERLAPPEDWINDOW) {
MONITORINFO mi = { sizeof(mi) };
if (GetWindowPlacement(hwnd, &g_wpPrev) &&
GetMonitorInfo(MonitorFromWindow(hwnd,
MONITOR_DEFAULTTOPRIMARY), &mi)) {
SetWindowLong(hwnd, GWL_STYLE,
dwStyle & ~WS_OVERLAPPEDWINDOW);
SetWindowPos(hwnd, HWND_TOP,
mi.rcMonitor.left, mi.rcMonitor.top,
mi.rcMonitor.right - mi.rcMonitor.left,
mi.rcMonitor.bottom - mi.rcMonitor.top,
SWP_NOOWNERZORDER | SWP_FRAMECHANGED);
}
}
else {
SetWindowLong(hwnd, GWL_STYLE,
dwStyle | WS_OVERLAPPEDWINDOW);
SetWindowPlacement(hwnd, &g_wpPrev);
SetWindowPos(hwnd, NULL, 0, 0, 0, 0,
SWP_NOMOVE | SWP_NOSIZE | SWP_NOZORDER |
SWP_NOOWNERZORDER | SWP_FRAMECHANGED);
}
}
int WINAPI WinMain(_In_ HINSTANCE hInstance, _In_opt_ HINSTANCE hPrevInstance, _In_ LPSTR szCmdLine, _In_ int iCmdShow)
{
static TCHAR szAppName[] = TEXT("hello windows");
HWND hwnd;
MSG msg;
WNDCLASS wndclass;
wndclass.style = CS_HREDRAW | CS_VREDRAW;
wndclass.lpfnWndProc = WndProc;
wndclass.cbClsExtra = 0;
wndclass.cbWndExtra = 0;
wndclass.hInstance = hInstance;
wndclass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
wndclass.hCursor = LoadCursor(NULL, IDC_ARROW);
wndclass.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wndclass.lpszMenuName = NULL;
wndclass.lpszClassName = szAppName;
if (!RegisterClass(&wndclass))
{
MessageBox(NULL, TEXT("This program requires Windows NT!"), szAppName, MB_ICONERROR);
}
hwnd = CreateWindow(szAppName,
TEXT("the hello program"),
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
CW_USEDEFAULT,
CW_USEDEFAULT,
NULL,
NULL,
hInstance,
NULL);
setFullWindow(hwnd);
ShowWindow(hwnd, iCmdShow);
UpdateWindow(hwnd);
while (GetMessageW(&msg, NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessageW(&msg);
}
return msg.wParam;
}
LRESULT CALLBACK WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
switch (message)
{
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hwnd, message, wParam, lParam);
}

How do I make a tab control with children elements?

I'm learning WINAPI, I read there's no children control in the sense a C#'s TabControl control does, so you have to create elements and show/hide by yourself. I read it may be done by drawing a dialog box inside tab page's area so I went to create a borderless dialog box being tab control's child, to make it have effect like C#'s. But I still couldn't make it. My dialog box is floating rather being tab control's child. I don't know to make it inside the tab page, I've tried setting the hWndParent to tab control's HWND and WS_EX_TOOLWINDOW | WS_EX_CONTROLPARENT flags in dwExStyle but still is floating over the tab control. Different approaches to solve this are welcome. I'm creating the tab control like this:
void AddTabControl(HWND hwnd)
{
hTab = CreateWindowW(WC_TABCONTROLW, NULL,
WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_TABSTOP,
0, 30, 250, 250,
hwnd,
(HMENU) 9,
NULL,
NULL);
InsertTabItem(hTab, 10, L"A");
InsertTabItem(hTab, 11, L"B");
}
void InsertTabItem(HWND tabHwnd, UINT id, LPWSTR text)
{
TCITEMW tci = {0};
tci.mask = TCIF_TEXT;
tci.pszText = text;
tci.cchTextMax = lstrlenW(text);
if(SendMessage(tabHwnd, TCM_INSERTITEMW, id, (LPARAM) &tci) == -1) {
MessageBox(NULL,
L"couldn't create the new tab page",
L"tab errror",
MB_OK | MB_ICONERROR);
}
}
And the dialog box like this:
void CreateDialogBox(HWND hwnd)
{
CreateWindowExW(WS_EX_TOOLWINDOW | WS_EX_CONTROLPARENT, // WS_EX_TOOLWINDOW to hide window from ALT+TAB
L"DialogClass", L"Dialog Box",
WS_VISIBLE | WS_POPUP | WS_SYSMENU,
100, 100, 400, 150,
hTab, NULL, ghInstance, NULL
);
}
the result is:
the expected result (made from C#, just for example, ignore the color differences, I'll fix this later):
here's the full code:
#pragma comment(lib, "user32.lib")
#pragma comment(lib, "Comctl32.lib")
#define UNICODE
#include <windows.h>
#include <Commctrl.h>
#include <strsafe.h>
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK DialogProc(HWND, UINT, WPARAM, LPARAM);
void CreateDialogBox(HWND);
void RegisterDialogClass(HWND);
void AddTabControl(HWND hwnd);
void InsertTabItem(HWND tabHwnd, UINT id, LPWSTR text);
HINSTANCE ghInstance;
HWND mainWindow;
HWND hTab;
int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
PWSTR pCmdLine, int nCmdShow) {
MSG msg = {0};
HWND hwnd;
WNDCLASSW wc = {0};
wc.lpszClassName = L"Window";
wc.hInstance = hInstance;
wc.hbrBackground = GetSysColorBrush(COLOR_3DFACE);
wc.lpfnWndProc = WndProc;
RegisterClassW(&wc);
hwnd = CreateWindowW(wc.lpszClassName, L"Window",
WS_OVERLAPPEDWINDOW | WS_VISIBLE,
100, 100, 500, 350, NULL, NULL, hInstance, NULL);
mainWindow = hwnd;
ghInstance = hInstance;
while( GetMessage(&msg, NULL, 0, 0)) {
DispatchMessage(&msg);
}
return (int) msg.wParam;
}
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch(msg)
{
case WM_CREATE:
RegisterDialogClass(hwnd);
AddTabControl(hwnd);
CreateDialogBox(hwnd);
break;
case WM_COMMAND:
CreateDialogBox(hwnd);
break;
case WM_DESTROY:
{
PostQuitMessage(0);
return 0;
}
}
return DefWindowProcW(hwnd, msg, wParam, lParam);
}
LRESULT CALLBACK DialogProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch(msg) {
case WM_CREATE:
CreateWindowW(L"button", L"A",
WS_VISIBLE | WS_CHILD ,
50, 50, 80, 25, hwnd, (HMENU) 1, NULL, NULL);
CreateWindowW(L"button", L"B",
WS_VISIBLE | WS_CHILD ,
150, 50, 80, 25, hwnd, (HMENU) 2, NULL, NULL);
CreateWindowW(L"button", L"C",
WS_VISIBLE | WS_CHILD ,
250, 50, 80, 25, hwnd, (HMENU) 3, NULL, NULL);
break;
case WM_COMMAND:
DestroyWindow(hwnd);
break;
case WM_CLOSE:
DestroyWindow(hwnd);
break;
}
return (DefWindowProcW(hwnd, msg, wParam, lParam));
}
void RegisterDialogClass(HWND hwnd)
{
WNDCLASSEXW wc = {0};
wc.cbSize = sizeof(WNDCLASSEXW);
wc.lpfnWndProc = (WNDPROC) DialogProc;
wc.hInstance = ghInstance;
wc.hbrBackground = GetSysColorBrush(COLOR_3DFACE);
wc.lpszClassName = L"DialogClass";
RegisterClassExW(&wc);
}
void CreateDialogBox(HWND hwnd)
{
CreateWindowExW(WS_EX_TOOLWINDOW | WS_EX_CONTROLPARENT, // WS_EX_TOOLWINDOW to hide window from ALT+TAB
L"DialogClass", L"Dialog Box",
WS_VISIBLE | WS_POPUP | WS_SYSMENU,
100, 100, 400, 150,
hTab, NULL, ghInstance, NULL
);
}
void AddTabControl(HWND hwnd)
{
hTab = CreateWindowW(WC_TABCONTROLW, NULL,
WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_TABSTOP,
0, 30, 250, 250,
hwnd,
(HMENU) 9,
NULL,
NULL);
InsertTabItem(hTab, 10, L"A");
InsertTabItem(hTab, 11, L"B");
}
void InsertTabItem(HWND tabHwnd, UINT id, LPWSTR text)
{
TCITEMW tci = {0};
tci.mask = TCIF_TEXT;
tci.pszText = text;
tci.cchTextMax = lstrlenW(text);
if(SendMessage(tabHwnd, TCM_INSERTITEMW, id, (LPARAM) &tci) == -1) {
MessageBox(NULL,
L"couldn't create the new tab page",
L"tab errror",
MB_OK | MB_ICONERROR);
}
}
When you created the dialog box control, you lacked the WS_CHILD style and added the WS_POPUP style, which caused the dialog box you generated to float.
You only need to modify it to the WS_CHILD style, and appropriately modify the size of the control to achieve your desired effect.
void CreateDialogBox(HWND hwnd)
{
CreateWindowExW(WS_EX_TOOLWINDOW | WS_EX_CONTROLPARENT, // WS_EX_TOOLWINDOW to hide window from ALT+TAB
L"DialogClass", L"Dialog Box",
WS_VISIBLE | WS_SYSMENU | WS_CHILD ,
10, 30, 350, 150,
hTab, NULL, ghInstance, NULL
);
}
void AddTabControl(HWND hwnd)
{
hTab = CreateWindowW(WC_TABCONTROLW, NULL,
WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_TABSTOP,
10, 30, 400, 250,
hwnd,
(HMENU)9,
NULL,
NULL);
InsertTabItem(hTab, 10, L"A");
InsertTabItem(hTab, 11, L"B");
}
It works like this:

Hiding and showing container windows based on tab

I have created a tab control that contains two tabs. Inside each tab there will be a container window to hold other controls (in the code example, a static control for instance). The idea is that when a new tab is selected, it will hide/show the correct container window that holds a bunch of controls. However I am struggling to get the container windows holding the static controls to show. This is the code so far:
#include <windows.h>
#include <commctrl.h>
#pragma comment(lib, "comctl32.lib")
#define ID_TABCTRL 1
#define ID_STATIC0 2
#define ID_STATIC1 3
#define ID_TAB0 4
#define ID_TAB1 5
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
HWND hTab, hTab0, hTab1;
int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PWSTR pCmdLine, int nCmdShow)
{
MSG msg;
WNDCLASS wc = { 0 };
wc.lpszClassName = TEXT("Tab control");
wc.hInstance = hInstance;
wc.hbrBackground = GetSysColorBrush(COLOR_3DFACE);
wc.lpfnWndProc = WndProc;
wc.hCursor = LoadCursor(0, IDC_ARROW);
RegisterClass(&wc);
CreateWindow(wc.lpszClassName, TEXT("Tab control"), WS_OVERLAPPEDWINDOW | WS_VISIBLE, 100, 100, 250, 200, 0, 0, hInstance, 0);
while (GetMessage(&msg, NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return (int)msg.wParam;
}
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
TCITEM tie;
INITCOMMONCONTROLSEX icex;
switch (msg)
{
case WM_CREATE:
icex.dwSize = sizeof(INITCOMMONCONTROLSEX);
icex.dwICC = ICC_TAB_CLASSES;
InitCommonControlsEx(&icex);
tie.mask = TCIF_TEXT;
///// Create Tab Control /////
hTab = CreateWindow(WC_TABCONTROL, NULL, WS_CHILD | WS_VISIBLE, 0, 0, 200, 150, hwnd, (HMENU)ID_TABCTRL, NULL, NULL);
///// Create Individual Tabs /////
tie.pszText = TEXT("First");
SendMessage(hTab, TCM_INSERTITEM, 0, (LPARAM)(LPTCITEM)&tie);
tie.pszText = TEXT("Second");
SendMessage(hTab, TCM_INSERTITEM, 1, (LPARAM)(LPTCITEM)&tie);
///// Create Container windows for each tab /////
hTab0 = CreateWindow(0, NULL, WS_CHILD | WS_VISIBLE, 0, 0, 200, 150, hTab, (HMENU)ID_TAB0, NULL, NULL);
hTab1 = CreateWindow(0, NULL, WS_CHILD, 0, 0, 200, 150, hTab, (HMENU)ID_TAB1, NULL, NULL);
///// Add example control to one of the tab container windows /////
CreateWindow(TEXT("Static"), TEXT("Yay!"), WS_CHILD | WS_VISIBLE | SS_LEFT, 20, 30, 50, 25, hTab0, (HMENU)ID_STATIC0, NULL, NULL);
CreateWindow(TEXT("Static"), TEXT("It appears to be working"), WS_CHILD | WS_VISIBLE | SS_LEFT, 20, 30, 100, 50, hTab1, (HMENU)ID_STATIC1, NULL, NULL);
break;
case WM_NOTIFY:
switch (((LPNMHDR)lParam)->code)
{
case TCN_SELCHANGE:
switch (TabCtrl_GetCurSel(hTab))
{
///// Show or Hide the appropriate tabs /////
case 0:
ShowWindow(hTab1, SW_HIDE);
ShowWindow(hTab0, SW_SHOW);
case 1:
ShowWindow(hTab0, SW_HIDE);
ShowWindow(hTab1, SW_SHOW);
}
}
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
}
return(DefWindowProc(hwnd, msg, wParam, lParam));
}
Is it just a case of the container windows hTab0 and hTab1 being stuck behind the tab window (hTab)?
First, you need to change the position of the tab and static form, otherwise it will block the generated content.
Then you can define the generated static text directly through CreateWindow, by using WC_STATIC.
#include <Windows.h>
#include <commctrl.h>
LRESULT CALLBACK WndProc(HWND, UINT,WPARAM,LPARAM);
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow)
{
static TCHAR szAppName[] = TEXT("windows");
HWND hwnd;
MSG msg;
WNDCLASS wndclass;
wndclass.style = CS_HREDRAW | CS_VREDRAW;
wndclass.lpfnWndProc = WndProc;
wndclass.cbClsExtra = 0;
wndclass.cbWndExtra = 0;
wndclass.hInstance = hInstance;
wndclass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
wndclass.hCursor = LoadCursor(NULL, IDC_ARROW);
wndclass.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wndclass.lpszMenuName = NULL;
wndclass.lpszClassName = szAppName;
if (!RegisterClass(&wndclass))
{
MessageBox(NULL, TEXT("This program requires Windows NT!"), szAppName, MB_ICONERROR);
}
hwnd = CreateWindow(szAppName,
TEXT("the hello program"),
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
CW_USEDEFAULT,
CW_USEDEFAULT,
NULL,
NULL,
hInstance,
NULL);
ShowWindow(hwnd,iCmdShow);
UpdateWindow(hwnd);
while (GetMessageW(&msg,NULL,0,0))
{
TranslateMessage(&msg);
DispatchMessageW(&msg);
}
return msg.wParam;
}
LRESULT CALLBACK WndProc(HWND hwnd, UINT message,WPARAM wParam,LPARAM lParam)
{
static HINSTANCE hInstance;
static HWND hwndTab = 0 , hwndStatic1,hwndStatic2;
TCITEM tie;
RECT rcClient;
INITCOMMONCONTROLSEX icex;
icex.dwSize = sizeof(INITCOMMONCONTROLSEX);
icex.dwICC = ICC_TAB_CLASSES;
TCHAR tabLBL1[256];
GetClientRect(hwnd, &rcClient);
switch (message)
{
case WM_CREATE:
{
hInstance = ((LPCREATESTRUCT)lParam)->hInstance;
hwndTab = CreateWindow(WC_TABCONTROL, L"",
WS_CHILD | WS_CLIPSIBLINGS | WS_VISIBLE,
0, 0, rcClient.right, rcClient.bottom,
hwnd, NULL, hInstance, NULL);
//Add tabs for each day of the week.
tie.mask = TCIF_TEXT | TCIF_IMAGE;
tie.iImage = -1;
wsprintf(tabLBL1, L"tab1");
tie.pszText = tabLBL1;
TabCtrl_InsertItem(hwndTab, 0, &tie);
wsprintf(tabLBL1, L"tab2");
TabCtrl_InsertItem(hwndTab, 1, &tie);
hwndStatic1 = CreateWindow(WC_STATIC, L"123",
WS_CHILD | WS_VISIBLE | WS_BORDER,
200, 200, 100, 100, // Position and dimensions; example only.
hwndTab, NULL, hInstance, // g_hInst is the global instance handle
NULL);
hwndStatic2 = CreateWindow(WC_STATIC, L"456",
WS_CHILD | WS_VISIBLE | WS_BORDER,
400, 200, 100, 100, // Position and dimensions; example only.
hwndTab, NULL, hInstance, // g_hInst is the global instance handle
NULL);
ShowWindow(hwndStatic1, TRUE);
ShowWindow(hwndStatic2, FALSE);
return 0;
}
case WM_DESTROY:
PostQuitMessage(0);
return 0;
case WM_NOTIFY:
if (((LPNMHDR)lParam)->code == TCN_SELCHANGE)
{
int tabID = TabCtrl_GetCurSel(hwndTab);
switch (tabID)
{
case 0:
ShowWindow(hwndStatic1, TRUE);
ShowWindow(hwndStatic2, FALSE);
break;
case 1:
ShowWindow(hwndStatic1, FALSE);
ShowWindow(hwndStatic2, TRUE);
break;
default:
break;
}
}
}
return DefWindowProc(hwnd, message, wParam, lParam);
}
Zhu Song's answer helped solved the problem (the container windows needing to be a static control, and needing to be positioned inside the tab control's space, below the clickable tabs).
Here is the result, swapping the two container window creation lines:
hTab0 = CreateWindow(TEXT("Static"), NULL, WS_CHILD | WS_VISIBLE, 1, 25, 197, 123, hTab, (HMENU)ID_TAB0, NULL, NULL);
hTab1 = CreateWindow(TEXT("Static"), NULL, WS_CHILD, 1, 25, 197, 123, hTab, (HMENU)ID_TAB1, NULL, NULL);
Note how the container window sizes and position are small enough to just fit inside the main tab control window (you can add WS_BORDER to the style to see where exactly it fits).

Control Size To Fit Window Size

I have a textbox on a form and i want to set it to match the height/width of the window. Is there any way to do this in C? To be clear this is C not C-Sharp (C#). I'm using DevC++
Code i have to create TextBox:
HWND hwndText = CreateWindow(
TEXT("edit"),
TEXT(""),
WS_VISIBLE | WS_CHILD | WS_BORDER | WS_HSCROLL | WS_VSCROLL| ES_MULTILINE | ES_AUTOHSCROLL,
0,0,
630,470, //Height & Width
hwnd,
(HMENU)ID_MYTEXT,
hInstance,
NULL
);
Full Source:
#include <windows.h>
const char g_szClassName[] = "myWindowClass";
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch(msg)
{
case WM_CLOSE:
DestroyWindow(hwnd);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return DefWindowProc(hwnd, msg, wParam, lParam);
}
return 0;
}
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
LPSTR lpCmdLine, int nCmdShow)
{
WNDCLASSEX wc;
HWND hwnd;
HMENU ID_MYTEXT;
MSG Msg;
wc.cbSize = sizeof(WNDCLASSEX);
wc.style = 0;
wc.lpfnWndProc = WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInstance;
wc.hIcon = LoadIcon(NULL, IDI_APPLICATION);
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
wc.hbrBackground = (HBRUSH)(COLOR_WINDOW+1);
wc.lpszMenuName = NULL;
wc.lpszClassName = g_szClassName;
wc.hIconSm = LoadIcon(NULL, IDI_APPLICATION);
if(!RegisterClassEx(&wc))
{
MessageBox(NULL, "Window Registration Failed!", "Error!",
MB_ICONEXCLAMATION | MB_OK);
return 0;
}
hwnd = CreateWindowEx(
WS_EX_CLIENTEDGE,
g_szClassName,
"Title",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT, 640, 480,
NULL, NULL, hInstance, NULL
);
HWND hwndText = CreateWindow(
TEXT("edit"),
TEXT(""),
WS_VISIBLE | WS_CHILD | WS_BORDER | WS_HSCROLL | WS_VSCROLL| ES_MULTILINE | ES_AUTOHSCROLL,
0,0,
630,470,
hwnd,
(HMENU)ID_MYTEXT,
hInstance,
NULL
);
if(hwnd == NULL)
{
MessageBox(NULL, "Window Creation Failed!", "Error!",
MB_ICONEXCLAMATION | MB_OK);
return 0;
}
ShowWindow(hwnd, nCmdShow);
UpdateWindow(hwnd);
SendMessage(hwndText, WM_SETTEXT, 0, (LPARAM)"");
while(GetMessage(&Msg, NULL, 0, 0) > 0)
{
TranslateMessage(&Msg);
DispatchMessage(&Msg);
}
return Msg.wParam;
}
If this is all you want to have in your window, then why not remove the WS_CHILD style and make the button the whole window?
The other alternative is to handle WM_SIZE message and resize your child button window there.
The shortest version of first example looks like this:
#include "stdafx.h"
BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{
HWND hWnd;
hWnd = CreateWindow(_T("BUTTON"), L"testButton", WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, hInstance, NULL);
if (!hWnd)
{
return FALSE;
}
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
return TRUE;
}
int APIENTRY _tWinMain(_In_ HINSTANCE hInstance,
_In_opt_ HINSTANCE hPrevInstance,
_In_ LPTSTR lpCmdLine,
_In_ int nCmdShow)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);
// TODO: Place code here.
MSG msg;
// Perform application initialization:
if (!InitInstance (hInstance, nCmdShow))
{
return FALSE;
}
// Main message loop:
while (GetMessage(&msg, NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return (int) msg.wParam;
}

Resources