I need to create a toolbar with texts only (without icons).
I have tried to do that, but the toolbar has appeared without anything (only gray strip on the top part of my window).
The program is below.
It is assumed then `CreateButtons2` function should create the toolbar.
Buttons texts are in `ButtonsArray`.
Could you tell what I am doing wrong ?
#pragma once
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <stdlib.h>
#include <malloc.h>
#include <memory.h>
#include <tchar.h>
// ----------------------------------------
#include <vector>
#include <string>
#include <assert.h>
#include <winuser.h>
#pragma comment( lib, "comctl32" )
#include <commctrl.h>
void DebugOutput_c(const char* msg) {
size_t convertedChars = 0;
size_t newsize = strlen(msg) + 1;
wchar_t* result_wstring = new wchar_t[newsize];
mbstowcs_s(&convertedChars, result_wstring, newsize, msg, _TRUNCATE);
OutputDebugStringW(result_wstring);
delete[] result_wstring;
}
void DebugOutput_w(const std::wstring& msg) {
OutputDebugStringW(msg.c_str());
}
void DebugOutput_s(const std::string s) {
DebugOutput_c(s.c_str());
}
HINSTANCE g_hInst;
const WCHAR* szMainWindowTitle = L"--- TEST ---";
const WCHAR* szMainWindowClass = L"WinClass";
HWND g_hMainWindow = NULL;
LRESULT CALLBACK WndProc_MainWin(HWND, UINT, WPARAM, LPARAM);
// ---------------------------------
struct ButtonDescription_STRUCT {
std::wstring Caption;
int ButtonID;
};
using ButtonDescriptions_ARRAY = std::vector<ButtonDescription_STRUCT>;
#define ID_BUTTON_1 1
#define ID_BUTTON_2 2
const ButtonDescriptions_ARRAY ButtonsArray = {
{L"PLUS", ID_BUTTON_1},
{L"MINUS", ID_BUTTON_2}
};
bool CreateButtons2(const ButtonDescriptions_ARRAY& ButtonsArray,
HINSTANCE hInst, HWND hMainWindow) {
bool ok = true;
HWND hToolbar = CreateWindowW(TOOLBARCLASSNAME, NULL,
TBSTYLE_WRAPABLE | WS_CHILD,
0, 0, 0, 0,
g_hMainWindow, NULL, hInst, NULL);
DWORD ErrCode = GetLastError();
assert(hToolbar != NULL);
RECT rect;
for (const ButtonDescription_STRUCT& b : ButtonsArray) {
DebugOutput_w(L"Next = " + b.Caption + L"n");
const int numButtons = 1;
TBBUTTON tb{ 0 };
tb.iBitmap = 0;
tb.idCommand = b.ButtonID;
tb.iString = (INT_PTR) b.Caption.c_str();
tb.fsState = TBSTATE_ENABLED;
tb.fsStyle = TBSTYLE_BUTTON | BTNS_SHOWTEXT; // BTNS_BUTTON;
WPARAM wParam = 1;
LPARAM lParam = (LPARAM)&tb;
int iNew = SendMessageW(hToolbar, TB_ADDBUTTONSW, wParam, lParam);
assert(iNew >= 0);
DebugOutput_s("iNew = " + std::to_string(iNew) + "n");
}
ShowWindow(hToolbar, SW_SHOW);
return ok;
}
ATOM RegisterClass_MainWin() {
WNDCLASSEXW wcex;
ZeroMemory(&wcex, sizeof(wcex));
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style = CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc = WndProc_MainWin;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = g_hInst;
wcex.hCursor = LoadCursor(nullptr, IDC_ARROW);
wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW + 1);
wcex.lpszClassName = szMainWindowClass;
return RegisterClassExW(&wcex);
}
BOOL InitInstance(HINSTANCE hInstance) {
g_hInst = hInstance;
g_hMainWindow = CreateWindowW(szMainWindowClass, szMainWindowTitle, WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, nullptr, nullptr, hInstance, nullptr);
if (!g_hMainWindow) {
return FALSE;
}
return TRUE;
}
void ShowAndUpdateWin(HWND hWnd, int nCmdShow) {
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
}
int APIENTRY wWinMain(_In_ HINSTANCE hInstance,
_In_opt_ HINSTANCE hPrevInstance,
_In_ LPWSTR lpCmdLine,
_In_ int nCmdShow)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);
INITCOMMONCONTROLSEX icex;
icex.dwSize = sizeof(icex);
icex.dwICC = ICC_BAR_CLASSES;
BOOL res_init = InitCommonControlsEx(&icex);
assert(res_init == TRUE);
RegisterClass_MainWin();
if (!InitInstance(g_hInst)) {
return FALSE;
}
CreateButtons2(ButtonsArray, g_hInst, g_hMainWindow);
ShowAndUpdateWin(g_hMainWindow, SW_NORMAL);
MSG msg;
while (GetMessage(&msg, nullptr, 0, 0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return (int)msg.wParam;
}
LRESULT CALLBACK WndProc_MainWin(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
switch (message)
{
case WM_COMMAND:
{
int wmId = LOWORD(wParam);
switch (wmId) {
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
}
break;
/*
case WM_PAINT: {
PAINTSTRUCT ps;
HDC hdc = BeginPaint(hWnd, &ps);
EndPaint(hWnd, &ps);
break;
}
*/
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
return 0;
}