CreateWindow “Edit” typed characters are 'invisible'? - winapi

After having researched all I could find on the proper syntax for the CreateWindow("Edit") call, I have to throw in the towel: when I run the program, all I get in the Edit box is "invisible characters". The cursor is moving right as I type, but the characters I enter are nowhere to be seen. Only when I select the box content with the mouse do I see the text. But as soon as I release the mouse, I can not longer see anything.
Here is the entire code which leads to 'text not showing' in the Edit control:
#include <windows.h>
#define FILE_MENU_NEW 1
#define FILE_MENU_OPEN 2
#define FILE_MENU_QUIT 3
#define CHANGE_TITLE 4
LRESULT CALLBACK WindowProc(HWND, UINT, WPARAM, LPARAM);
void AddMenus(HWND);
void AddControls(HWND);
HMENU hMenu;
HWND hEdit;
int WINAPI wWinMain(_In_ HINSTANCE hInstance, _In_opt_ HINSTANCE hPrevInstance, _In_ LPWSTR lpCmdLine, _In_ int nShowCmd)
{
WNDCLASS wc = {0}; // Assign 0 to all its elements initialy
wc.hbrBackground = (HBRUSH)COLOR_WINDOW;
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
wc.hInstance = hInstance;
wc.lpszClassName = L"myWindowClass";
wc.lpfnWndProc = WindowProc; // this is a pointer to a function
if(!RegisterClass(&wc))
return -1;
HWND hwnd = CreateWindowEx(
WS_EX_CLIENTEDGE,
L"myWindowClass",
L"Learn to Program Windows - Roger Breton",
WS_OVERLAPPEDWINDOW | WS_VISIBLE ,
100, 100, 800, 600,
NULL,
NULL,
hInstance,
NULL
);
if (hwnd == NULL)
{
return 0;
}
MSG msg = { };
while (GetMessage(&msg, NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return 0;
}
LRESULT CALLBACK WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
switch (uMsg)
{
case WM_COMMAND:
switch(wParam)
{
case FILE_MENU_QUIT:
DestroyWindow(hWnd);
break;
case FILE_MENU_NEW:
MessageBeep(MB_ICONINFORMATION);
break;
case CHANGE_TITLE:
wchar_t text[100];
GetWindowTextW(hEdit, text, 100);
SetWindowTextW(hWnd, text);
break;
}
case WM_CREATE:
AddMenus(hWnd);
AddControls(hWnd);
break;
case WM_DESTROY:
PostQuitMessage(0);
return 0;
case WM_PAINT:
{
PAINTSTRUCT ps;
HDC hdc = BeginPaint(hWnd, &ps);
FillRect(hdc, &ps.rcPaint, (HBRUSH)(COLOR_WINDOW));
EndPaint(hWnd, &ps);
}
return 0;
}
return DefWindowProc(hWnd, uMsg, wParam, lParam);
}
void AddMenus(HWND hWnd)
{
hMenu = CreateMenu();
HMENU hFileMenu = CreateMenu();
HMENU hSubMenu = CreateMenu();
AppendMenu(hSubMenu, MF_STRING, NULL, L"Sub-Menu");
AppendMenu(hFileMenu, MF_STRING, FILE_MENU_NEW, L"New");
AppendMenu(hFileMenu, MF_POPUP, (UINT_PTR)hSubMenu, L"Sub-menu ");
AppendMenu(hFileMenu, MF_SEPARATOR, NULL, NULL);
AppendMenu(hFileMenu, MF_STRING, FILE_MENU_QUIT, L"Quit");
AppendMenu(hMenu, MF_POPUP, (UINT_PTR)hFileMenu, L"File");
AppendMenu(hMenu, MF_STRING, NULL, L"Aide");
SetMenu(hWnd, hMenu);
}
void AddControls(HWND hWnd)
{
CreateWindowW(L"Static", L"Enter text here:", WS_VISIBLE | WS_CHILD | WS_BORDER | SS_CENTER , 200, 100, 150, 50, hWnd, NULL, NULL, NULL);
hEdit = CreateWindowW(L"Edit", NULL, WS_VISIBLE | WS_CHILD | WS_BORDER , 200, 152, 100, 50, hWnd, NULL, NULL, NULL);
CreateWindowW(L"Button", L"Changez title", WS_VISIBLE | WS_CHILD, 200, 204, 150, 50, hWnd, (HMENU)CHANGE_TITLE, NULL, NULL);
}
I tried to recreate the source file many times, to no avail.

You have a missing break; statement at the end of your case WM_COMMAND: block. As it stands, your code will 'fall through' to the case WM_CREATE: code after processing any WM_COMMAND.
Adding that break; statement appears to fix your code (when I test it):
LRESULT CALLBACK WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
switch (uMsg) {
case WM_COMMAND:
switch (wParam) {
case FILE_MENU_QUIT:
DestroyWindow(hWnd);
break;
case FILE_MENU_NEW:
MessageBeep(MB_ICONINFORMATION);
break;
case CHANGE_TITLE:
wchar_t text[100];
GetWindowTextW(hEdit, text, 100);
SetWindowTextW(hWnd, text);
break;
}
break; // ** You missed this line! **
case WM_CREATE:
AddMenus(hWnd);
AddControls(hWnd);
break;
//...
Such mistakes can be spotted if you enable all compiler warnings: The static code analyser in MSVC gives the following message:
warning C26819: Unannotated fallthrough between switch labels (es.78).

Related

Message after clicking on the edit control

I’m new to WinAPI development.
The main window contains three Edit controls.When clicking with the left mouse button on Edit1, the message "Edit1 choosed" is to be displayed. When you click on Edit2, it is supposed to display the message "Edit2 choosed". Similarly, when you click on Edit3, the message "Edit3 choosed" should be displayed. I tried using various combinations of WM_LBUTTONDOWN and WM_SETFOCUS, unfortunately the program does not work. Could someone please help me?
#include <windows.h>
#define Edit1 501
#define Edit2 502
#define Edit3 503
HWND TextBox1, TextBox2, TextBox3;
HFONT HF = CreateFont (30, 0, 00, 00, FW_DONTCARE, FALSE, FALSE, FALSE, ANSI_CHARSET,
OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, "Arial");
LRESULT CALLBACK WndProc(HWND hwnd, UINT Message, WPARAM wParam, LPARAM lParam) {
switch(Message)
{
case WM_SETFOCUS:
if(wParam == Edit1)
{
MessageBox(NULL, "Edit1 choosed","Edit1",MB_ICONEXCLAMATION|MB_OK);
}
break;
if(wParam == Edit2)
{
MessageBox(NULL, "Edit2 choosed","Edit2",MB_ICONEXCLAMATION|MB_OK);
}
break;
if(wParam == Edit3)
{
MessageBox(NULL, "Edit3 choosed","Edit3",MB_ICONEXCLAMATION|MB_OK);
}
break;
case WM_CREATE:
{
TextBox1 = CreateWindowEx( WS_EX_CLIENTEDGE, "EDIT", NULL, WS_CHILD | WS_VISIBLE | WS_BORDER | ES_RIGHT,
30, 70, 190, 40, hwnd, (HMENU)Edit1, GetModuleHandle(NULL), NULL);
SendMessage(TextBox1, WM_SETFONT,( WPARAM ) HF, 0 );
TextBox2 = CreateWindowEx( WS_EX_CLIENTEDGE, "EDIT", NULL, WS_CHILD | WS_VISIBLE | WS_BORDER | ES_RIGHT,
30, 130, 190, 40, hwnd, (HMENU)Edit2, GetModuleHandle(NULL), NULL);
SendMessage(TextBox2, WM_SETFONT,( WPARAM ) HF, 0 );
TextBox3 = CreateWindowEx( WS_EX_CLIENTEDGE, "EDIT", NULL, WS_CHILD | WS_VISIBLE | WS_BORDER | ES_RIGHT,
30, 190, 190, 40, hwnd, (HMENU)Edit3, GetModuleHandle(NULL), NULL);
SendMessage(TextBox3, WM_SETFONT,( WPARAM ) HF, 0 );
break;
}
case WM_DESTROY:
{
PostQuitMessage(0);
break;
}
default:
return DefWindowProc(hwnd, Message, wParam, lParam);
}
return 0;
}
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
WNDCLASSEX wc;
HWND hwnd;
MSG msg;
memset(&wc,0,sizeof(wc));
wc.cbSize = sizeof(WNDCLASSEX);
wc.lpfnWndProc = WndProc;
wc.hInstance = hInstance;
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
wc.hbrBackground = (HBRUSH)(COLOR_WINDOW+1);
wc.lpszClassName = "WindowClass";
wc.hIcon = LoadIcon(NULL, IDI_APPLICATION);
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,"WindowClass","Caption",WS_VISIBLE|WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT, 640, 480, NULL,NULL,hInstance,NULL);
if(hwnd == NULL) {
MessageBox(NULL, "Window Creation Failed!","Error!",MB_ICONEXCLAMATION|MB_OK);
return 0;
}
while(GetMessage(&msg, NULL, 0, 0) > 0)
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return msg.wParam;
}
the "break" in the message loop under WM_SETFOCUS is always executed. So the program never reaches the point of the second edit control. Move the break to before the closing "}" and retry.
{
MessageBox(NULL, "Edit1 choosed","Edit1",MB_ICONEXCLAMATION|MB_OK);
break;
}
Furthermore, consider using 'else if'.

How do I detect a WM_KEYDOWN on child window?

For a standard control like button, edit, etc I can subclass it but how is this done for a child window(I'm using as a container)? I know the WM_KEYDOWN is sent to the parent window but I couldn't get it directly from the respective child window. I've tried subclassing it(not sure if this does make sense since it's a window and has its own window procedure already in the WNDCLASSW.lpfnWndProc member) but this subprocedure didn't get a WM_KEYDOWN message anyway. I can get the control's hwnd from the cursor position (I need to consider keyboard focus too) by using GetCursorPos() and WindowFromPoint() like below but I feel it's hacky. What's the proper way to do this?
currently it look like this:
case WM_KEYUP:
case WM_KEYDOWN:
{
POINT p;
if(GetCursorPos(&p))
{
HWND control = WindowFromPoint(p);
if(control)
{
// just testing it
int len = GetWindowTextLength(control);
wchar_t buffer[len + 1];
GetWindowText(control, buffer, sizeof(buffer));
MessageBox(NULL, buffer, L"", MB_OK);
}
}
}
break;
the window look like this:
the goal is catch the WM_KEYDOWN on the respective window where the user typed something, then call a function to deal with this event, like window1_onKeyDown(), window2_onKeyDown() and such.
Here's full code:
#pragma comment(lib, "user32.lib")
#pragma comment(lib, "Comctl32.lib")
#pragma comment(lib, "Gdi32.lib")
#define WIN32_LEAN_AND_MEAN
#define UNICODE
#define _UNICODE
#include <windows.h>
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK WndProc1(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
LRESULT CALLBACK WndProc2(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
void createWindow1(HWND);
void createWindow2(HWND);
HBRUSH hBrush1, hBrush2;
int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
PWSTR lpCmdLine, int nCmdShow) {
MSG msg;
WNDCLASSW wc = {0};
wc.lpszClassName = L"my window";
wc.hInstance = hInstance;
wc.hbrBackground = GetSysColorBrush(COLOR_3DFACE);
wc.lpfnWndProc = WndProc;
wc.hCursor = LoadCursor(0, IDC_ARROW);
hBrush1 = CreateSolidBrush(RGB(173, 164, 237));
hBrush2 = CreateSolidBrush(RGB(171, 171, 171));
RegisterClassW(&wc);
CreateWindowW(wc.lpszClassName, L"window",
WS_OVERLAPPEDWINDOW | WS_VISIBLE,
100, 100, 330, 270, NULL, 0, hInstance, 0);
while (GetMessage(&msg, NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
DeleteObject(hBrush1);
DeleteObject(hBrush2);
return (int) msg.wParam;
}
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg,
WPARAM wParam, LPARAM lParam) {
switch(msg)
{
case WM_CREATE:
createWindow1(hwnd);
createWindow2(hwnd);
break;
case WM_KEYUP:
case WM_KEYDOWN:
{
POINT p;
if(GetCursorPos(&p))
{
HWND control = WindowFromPoint(p);
if(control)
{
int len = GetWindowTextLength(control);
wchar_t buffer[len + 1];
GetWindowText(control, buffer, sizeof(buffer));
MessageBox(NULL, buffer, L"", MB_OK);
}
}
}
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
}
return DefWindowProcW(hwnd, msg, wParam, lParam);
}
void createWindow1(HWND hOwner)
{
WNDCLASSW wc = {0};
wc.lpszClassName = L"window2";
wc.hInstance = NULL;
wc.hbrBackground = hBrush1;
wc.lpfnWndProc = WndProc1;
wc.hCursor = LoadCursor(0, IDC_ARROW);
RegisterClassW(&wc);
CreateWindowW(wc.lpszClassName, L"window2",
WS_VISIBLE | WS_TABSTOP | WS_CHILD | WS_EX_CONTROLPARENT,
5, 5, 200, 100,
hOwner, 0, NULL, 0);
}
void createWindow2(HWND hOwner)
{
WNDCLASSW wc = {0};
wc.lpszClassName = L"window3";
wc.hInstance = NULL;
wc.hbrBackground = hBrush2;
wc.lpfnWndProc = WndProc2;
wc.hCursor = LoadCursor(0, IDC_ARROW);
RegisterClassW(&wc);
CreateWindowW(wc.lpszClassName, L"window3",
WS_VISIBLE | WS_TABSTOP | WS_CHILD,
5, 120, 200, 100,
hOwner, 0, NULL, 0);
}
LRESULT CALLBACK WndProc1(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch(msg)
{
case WM_CREATE:
CreateWindow(L"Button", L"Button A",
WS_VISIBLE | WS_TABSTOP | WS_CHILD,
5, 5, 80, 25,
hwnd, 0, NULL, 0);
break;
case WM_KEYUP:
case WM_KEYDOWN:
MessageBox(NULL, L"hello from proc1", L"", MB_OK);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
}
return DefWindowProcW(hwnd, msg, wParam, lParam);
}
LRESULT CALLBACK WndProc2(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch(msg)
{
case WM_CREATE:
CreateWindow(L"Button", L"Button ",
WS_VISIBLE | WS_TABSTOP | WS_CHILD,
5, 5, 80, 25,
hwnd, 0, NULL, 0);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
}
return DefWindowProcW(hwnd, msg, wParam, lParam);
}
You can use SetFocus in the child window.
Some code:
case WM_KEYDOWN:
{
POINT p;
HWND control = GetFocus();
if (control)
{
int len = GetWindowTextLength(control);
wchar_t* buffer = new wchar_t[len + 1];
GetWindowText(control, buffer, len + 1);
MessageBox(NULL, buffer, L"", MB_OK);
}
}
break;
LRESULT CALLBACK WndProc1(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch (msg)
{
case WM_CREATE:
CreateWindow(L"Button", L"Button A",
WS_VISIBLE | WS_TABSTOP | WS_CHILD,
5, 5, 80, 25,
hwnd, 0, NULL, 0);
break;
case WM_LBUTTONDOWN:
SetFocus(hwnd);
break;
case WM_KEYUP:
case WM_KEYDOWN:
MessageBox(NULL, L"hello from proc1", L"", MB_OK);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
}
return DefWindowProcW(hwnd, msg, wParam, lParam);
}
You can also use the current method, and then use PostMessage/SendMessage to forward the WM_KEYDOWN message to the child window:
if (control)
{
int len = GetWindowTextLength(control);
wchar_t* buffer = new wchar_t[len + 1];
GetWindowText(control, buffer, len + 1);
MessageBox(NULL, buffer, L"", MB_OK);
PostMessage(hwnd_child, msg, wParam, lParam);
}

How do i detect the control that sent the WM_KEYDOWN?

WM_KEYDOWN message sends the message to the main window, I'd like to get control that originated the message. I've tried with GetFocus() handling WM_KEYDOWN like below but it didn't do anything, even when a press a key with focus on the buttona. How is that done? what am I missing?
Here's how I'm handling WM_KEYDOWN:
case WM_KEYDOWN:
HWND hFocus = GetFocus();
if(hFocus == buttonA)
{
buttona_onKeyDown();
}
else if(hFocus == buttonB)
{
buttonb_onKeyDown();
}
else
{
//MessageBox(NULL, L"Not found!", L"", MB_OK);
}
break;
full code:
#pragma comment(lib, "user32.lib")
#pragma comment(lib, "Comctl32.lib")
#pragma comment(lib, "Gdi32.lib")
#define WIN32_LEAN_AND_MEAN
#define UNICODE
#define _UNICODE
#include <windows.h>
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
void buttona_onKeyDown();
void buttonb_onKeyDown();
HWND buttonA, buttonB;
int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
PWSTR lpCmdLine, int nCmdShow) {
MSG msg;
WNDCLASSW wc = {0};
wc.lpszClassName = L"Buttons";
wc.hInstance = hInstance;
wc.hbrBackground = GetSysColorBrush(COLOR_3DFACE);
wc.lpfnWndProc = WndProc;
wc.hCursor = LoadCursor(0, IDC_ARROW);
RegisterClassW(&wc);
HWND hWnd =
CreateWindowW(wc.lpszClassName, L"Buttons",
WS_OVERLAPPEDWINDOW | WS_VISIBLE,
150, 150, 300, 200, 0, 0, hInstance, 0);
while (GetMessage(&msg, NULL, 0, 0))
{
if (!IsDialogMessage(hWnd, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return (int) msg.wParam;
}
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg,
WPARAM wParam, LPARAM lParam) {
switch(msg)
{
case WM_CREATE:
buttonA =
CreateWindowW(L"Button", L"A",
WS_VISIBLE | WS_CHILD | WS_TABSTOP,
20, 50, 80, 25, hwnd, (HMENU) 10, NULL, NULL);
buttonB =
CreateWindowW(L"Button", L"B",
WS_VISIBLE | WS_CHILD | WS_TABSTOP,
120, 50, 80, 25, hwnd, (HMENU) 11, NULL, NULL);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
case WM_KEYDOWN:
HWND hFocus = GetFocus();
if(hFocus == buttonA)
{
buttona_onKeyDown();
}
else if(hFocus == buttonB)
{
buttonb_onKeyDown();
}
else
{
//MessageBox(NULL, L"Not found!", L"", MB_OK);
}
break;
}
return DefWindowProcW(hwnd, msg, wParam, lParam);
}
void buttona_onKeyDown()
{
MessageBox(NULL, L"A OnKeyDown", L"", MB_OK);
}
void buttonb_onKeyDown()
{
MessageBox(NULL, L"B OnKeyDown", L"", MB_OK);
}

TreeView item lost higlight color after minimize

I have simple win32 application (not dialog box), and treeview in this application.
All works, but if I have selected item in the treeview, and I minimize and restore application, selected item changes blue higlighting color to grayed color.
How to correct this without using custom draw?
If I have treeview in the dialog box, selected item has always blue color.
CODE:
HWND g_hTree;
// Forward declarations of functions included in this code module:
ATOM MyRegisterClass(HINSTANCE hInstance);
BOOL InitInstance(HINSTANCE, int);
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
INT_PTR CALLBACK About(HWND, UINT, WPARAM, LPARAM);
HINSTANCE hInst;
int APIENTRY _tWinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);
// TODO: Place code here.
MSG Msg;
MyRegisterClass(hInstance);
// Perform application initialization:
if (!InitInstance (hInstance, nCmdShow))
{
return FALSE;
}
while(GetMessage(&Msg, NULL, 0, 0) > 0)
{
TranslateMessage(&Msg);
DispatchMessage(&Msg);
}
return (int) Msg.wParam;
}
ATOM MyRegisterClass(HINSTANCE hInstance)
{
WNDCLASSEX wcex;
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style = CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc = WndProc;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = hInstance;
wcex.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_TREEVIEWTEST));
wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW+1);
wcex.lpszMenuName = MAKEINTRESOURCE(IDC_TREEVIEWTEST);
wcex.lpszClassName = L"TreeViewTestClass";
wcex.hIconSm = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_SMALL));
return RegisterClassEx(&wcex);
}
BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{
HWND hWnd;
InitCommonControls();
hInst = hInstance; // Store instance handle in our global variable
hWnd = CreateWindow(L"TreeViewTestClass", L"Tree View Test", WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, hInstance, NULL);
if (!hWnd)
{
return FALSE;
}
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
return TRUE;
}
void AddItems();
#define TVS_STYLES (TVS_HASLINES | TVS_LINESATROOT | TVS_HASBUTTONS | TVS_SHOWSELALWAYS | TVS_INFOTIP | TVS_TRACKSELECT | WS_VSCROLL | WS_TABSTOP)
#define ID_TREEVIEW 505
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
int wmId, wmEvent;
PAINTSTRUCT ps;
HDC hdc;
switch (message)
{
case WM_COMMAND:
wmId = LOWORD(wParam);
wmEvent = HIWORD(wParam);
// Parse the menu selections:
switch (wmId)
{
case IDM_EXIT:
DestroyWindow(hWnd);
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
break;
case WM_CREATE:
{
g_hTree = CreateWindowEx(0, WC_TREEVIEWW, L"Test_Tree_View", WS_CHILD | WS_VISIBLE | WS_BORDER | TVS_STYLES, 10, 10, 240, 480, hWnd, (HMENU)ID_TREEVIEW, NULL, NULL);
AddItems();
}
break;
case WM_PAINT:
hdc = BeginPaint(hWnd, &ps);
// TODO: Add any drawing code here...
EndPaint(hWnd, &ps);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
return 0;
}
void AddItems()
{
TVITEM tvi;
HTREEITEM htSelected;
TVINSERTSTRUCT tvinsert; // struct to config out tree control
HTREEITEM htParent; // Tree item handle
HTREEITEM htBefore; // .......
HTREEITEM htRoot;
tvinsert.hParent=NULL; // top most level no need handle
tvinsert.hInsertAfter=TVI_ROOT; // work as root level
tvinsert.item.mask=TVIF_TEXT|TVIF_IMAGE|TVIF_SELECTEDIMAGE;
tvinsert.item.pszText=L"Parent1";
tvinsert.item.iImage=0;
tvinsert.item.iSelectedImage=1;
htParent = TreeView_InsertItem(g_hTree, &tvinsert);
htRoot = htParent;
htBefore = htParent;
tvinsert.hParent=htParent; // handle of the above data
tvinsert.hInsertAfter=TVI_LAST; // below parent
tvinsert.item.pszText=L"Child 1";
htParent = TreeView_InsertItem(g_hTree, &tvinsert);
tvinsert.hParent=htParent;
tvinsert.item.pszText=L"Child Of Child 1";
htParent = TreeView_InsertItem(g_hTree, &tvinsert);
tvinsert.hParent=htBefore; // handle of the above data
tvinsert.hInsertAfter=TVI_LAST; // below parent
tvinsert.item.pszText=L"Child 2";
htParent = TreeView_InsertItem(g_hTree, &tvinsert);
tvinsert.hParent=NULL; // top most level no need handle
tvinsert.hInsertAfter=TVI_LAST; // work as root level
tvinsert.item.pszText=L"Parent2";
htParent = TreeView_InsertItem(g_hTree, &tvinsert);
}
It seems your tree-view control is losing focus when the window is minimized. You can try handling WM_ACTIVATE and using SetFocus to manually set focus to the tree-view control.

after createwindow GetLastError return code 126 but the windows is create in win7 vc express

I using VC 2010 in win7 pc, and I have been getting an error 126 when creating a window setting lpszMenuName = 0 on the WNDCLASSEX structure the windows is create but get GetLastError the code is could be any I just created a project using the wizard and the same code it generate to create a simple windows with a menu if I set the lpszMenuName to 0.
#include "stdafx.h"
#include "simple.h"
#define MAX_LOADSTRING 100
// Global Variables:
HINSTANCE hInst; // current instance
TCHAR szTitle[MAX_LOADSTRING]; // The title bar text
TCHAR szWindowClass[MAX_LOADSTRING]; // the main window class name
// Forward declarations of functions included in this code module:
ATOM MyRegisterClass(HINSTANCE hInstance);
BOOL InitInstance(HINSTANCE, int);
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
INT_PTR CALLBACK About(HWND, UINT, WPARAM, LPARAM);
int APIENTRY _tWinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);
// TODO: Place code here.
MSG msg;
HACCEL hAccelTable;
// Initialize global strings
LoadString(hInstance, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);
LoadString(hInstance, IDC_SIMPLE, szWindowClass, MAX_LOADSTRING);
MyRegisterClass(hInstance);
// Perform application initialization:
if (!InitInstance (hInstance, nCmdShow))
{
return FALSE;
}
hAccelTable = LoadAccelerators(hInstance, MAKEINTRESOURCE(IDC_SIMPLE));
// Main message loop:
while (GetMessage(&msg, NULL, 0, 0))
{
if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return (int) msg.wParam;
}
in this function when registering the window I set wcex.lpszMenuName = 0
ATOM MyRegisterClass(HINSTANCE hInstance)
{
WNDCLASSEX wcex;
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style = CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc = WndProc;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = hInstance;
wcex.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_SIMPLE));
wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW+1);
wcex.lpszMenuName = 0;
wcex.lpszClassName = szWindowClass;
wcex.hIconSm = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_SMALL));
return RegisterClassEx(&wcex);
}
here in this function I wrote GetLastError( ) to test for error
BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{
HWND hWnd;
hInst = hInstance; // Store instance handle in our global variable
hWnd = CreateWindow(szWindowClass, szTitle, WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, hInstance, NULL);
DWORD eNum = GetLastError( );
if(eNum){
::MessageBox(hWnd, L"Error after creating windows", L"who cares", MB_OK | MB_ICONINFORMATION);
}
if (!hWnd)
{
return FALSE;
}
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
return TRUE;
}
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
int wmId, wmEvent;
PAINTSTRUCT ps;
HDC hdc;
switch (message)
{
case WM_COMMAND:
wmId = LOWORD(wParam);
wmEvent = HIWORD(wParam);
// Parse the menu selections:
switch (wmId)
{
case IDM_ABOUT:
DialogBox(hInst, MAKEINTRESOURCE(IDD_ABOUTBOX), hWnd, About);
break;
case IDM_EXIT:
DestroyWindow(hWnd);
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
break;
case WM_PAINT:
hdc = BeginPaint(hWnd, &ps);
// TODO: Add any drawing code here...
EndPaint(hWnd, &ps);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
return 0;
}
// Message handler for about box.
INT_PTR CALLBACK About(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{
UNREFERENCED_PARAMETER(lParam);
switch (message)
{
case WM_INITDIALOG:
return (INT_PTR)TRUE;
case WM_COMMAND:
if (LOWORD(wParam) == IDOK || LOWORD(wParam) == IDCANCEL)
{
EndDialog(hDlg, LOWORD(wParam));
return (INT_PTR)TRUE;
}
break;
}
return (INT_PTR)FALSE;
}
as you can see is pretty much the same code that the wizard generated I only set wcex.lpszMenuName=0 and add a GetLastError with a messagebox.
I just realize that if Run vc as administrator fix the

Resources