Make the toolbar a bit more attractive.
[reactos.git] / reactos / subsys / system / servman / servman.c
1 /*
2 * PROJECT: ReactOS Services
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: subsys/system/servman/servman.c
5 * PURPOSE: Main window message handler
6 * COPYRIGHT: Copyright 2005 Ged Murphy <gedmurphy@gmail.com>
7 *
8 */
9
10 #include "servman.h"
11
12 const TCHAR ClassName[] = _T("ServiceManager");
13
14 HINSTANCE hInstance;
15 HWND hMainWnd;
16 HWND hListView;
17 HWND hStatus;
18 HWND hTool;
19
20
21 LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
22 {
23 switch(msg)
24 {
25 case WM_CREATE:
26 {
27 //HFONT hfDefault;
28
29 HWND hTool;
30 TBADDBITMAP tbab;
31 INT iImageOffset;
32 INT statwidths[] = {110, -1};
33 TCHAR szTemp[256];
34 RECT rcClient;
35 LVCOLUMN lvc = { 0 };
36
37 /* Toolbar buttons */
38 TBBUTTON tbb [NUM_BUTTONS] =
39 { // iBitmap, idCommand, fsState, fsStyle, bReserved[2], dwData, iString
40 {TBICON_PROP, ID_PROP, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0}, /* properties */
41 {TBICON_REFRESH, ID_REFRESH, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0}, /* refresh */
42 {TBICON_EXPORT, ID_EXPORT, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0}, /* export */
43
44 /* Note: First item for a seperator is its width in pixels */
45 {5, 0, TBSTATE_ENABLED, BTNS_SEP, {0}, 0, 0}, /* separator */
46
47 {TBICON_START, ID_START, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0 }, /* start */
48 {TBICON_STOP, ID_STOP, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0 }, /* stop */
49 {TBICON_PAUSE, ID_PAUSE, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0 }, /* pause */
50 {TBICON_RESTART, ID_RESTART, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0 }, /* restart */
51
52 {5, 0, TBSTATE_ENABLED, BTNS_SEP, {0}, 0, 0}, /* separator */
53
54 {TBICON_NEW, ID_NEW, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0 }, /* start */
55 {TBICON_HELP, ID_HELP, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0 }, /* stop */
56 {TBICON_EXIT, ID_EXIT, TBSTATE_ENABLED, BTNS_BUTTON, {0}, 0, 0 }, /* pause */
57
58 };
59
60 /* ======================== Create Toolbar ============================== */
61
62 /* Create Toolbar */
63 hTool = CreateWindowEx(0,
64 TOOLBARCLASSNAME,
65 NULL,
66 WS_CHILD | WS_VISIBLE | TBSTYLE_FLAT | TBSTYLE_TOOLTIPS,
67 0, 0, 0, 0,
68 hwnd,
69 (HMENU)IDC_TOOLBAR,
70 hInstance,
71 NULL);
72 if(hTool == NULL)
73 MessageBox(hwnd, _T("Could not create tool bar."), _T("Error"), MB_OK | MB_ICONERROR);
74
75 /* Send the TB_BUTTONSTRUCTSIZE message, which is required for backward compatibility */
76 SendMessage(hTool, TB_BUTTONSTRUCTSIZE, sizeof(TBBUTTON), 0);
77
78 /* Add standard image list */
79 tbab.hInst = HINST_COMMCTRL;
80 tbab.nID = IDB_STD_SMALL_COLOR;
81 SendMessage(hTool, TB_ADDBITMAP, 0, (LPARAM) &tbab);
82
83 /* Add custom images */
84 tbab.hInst = hInstance;
85 tbab.nID = IDB_BUTTONS;
86 iImageOffset = (INT)SendMessage(hTool, TB_ADDBITMAP, 11, (LPARAM)&tbab);
87 tbb[0].iBitmap += iImageOffset; /* properties */
88 tbb[1].iBitmap += iImageOffset; /* refresh */
89 tbb[2].iBitmap += iImageOffset; /* export */
90 tbb[4].iBitmap += iImageOffset; /* start */
91 tbb[5].iBitmap += iImageOffset; /* stop */
92 tbb[6].iBitmap += iImageOffset; /* pause */
93 tbb[7].iBitmap += iImageOffset; /* restart */
94 tbb[9].iBitmap += iImageOffset; /* new */
95 tbb[10].iBitmap += iImageOffset; /* help */
96 tbb[11].iBitmap += iImageOffset; /* exit */
97
98 /* Add buttons to toolbar */
99 SendMessage(hTool, TB_ADDBUTTONS, NUM_BUTTONS, (LPARAM) &tbb);
100
101 /* Send a WM_SIZE message to layout controls */
102 GetClientRect(hwnd, &rcClient);
103 SendMessage(hwnd, WM_SIZE, SIZE_RESTORED, MAKELONG(rcClient.right, rcClient.bottom));
104
105 /* Show toolbar */
106 ShowWindow(hTool, SW_SHOWNORMAL);
107
108
109
110 /* ======================== Create List View ============================== */
111
112 hListView = CreateWindow(WC_LISTVIEW,
113 NULL,
114 WS_CHILD | WS_VISIBLE | LVS_REPORT | WS_BORDER |
115 LVS_EDITLABELS | LVS_SORTASCENDING,
116 0, 0, 0, 0, /* sized via WM_SIZE */
117 hwnd,
118 (HMENU) IDC_SERVLIST,
119 hInstance,
120 NULL);
121 if (hListView == NULL)
122 MessageBox(hwnd, _T("Could not create List View."), _T("Error"), MB_OK | MB_ICONERROR);
123
124
125
126 ListView_SetExtendedListViewStyle(hListView, LVS_EX_FULLROWSELECT |
127 /*LVS_EX_GRIDLINES |*/ LVS_EX_HEADERDRAGDROP);
128
129 lvc.mask = LVCF_TEXT | LVCF_SUBITEM | LVCF_WIDTH | LVCF_FMT;
130 lvc.fmt = LVCFMT_LEFT;
131
132 /* Add columns to the list-view (first column contains check box). */
133 lvc.iSubItem = 0;
134 lvc.cx = 160;
135 LoadString(hInstance, IDS_FIRSTCOLUMN, szTemp, 256);
136 lvc.pszText = szTemp;
137 ListView_InsertColumn(hListView, 0, &lvc);
138
139 lvc.iSubItem = 1;
140 lvc.cx = 260;
141 LoadString(hInstance, IDS_SECONDCOLUMN, szTemp, 256);
142 lvc.pszText = szTemp;
143 ListView_InsertColumn(hListView, 1, &lvc);
144
145 lvc.iSubItem = 2;
146 lvc.cx = 75;
147 LoadString(hInstance, IDS_THIRDCOLUMN, szTemp, 256);
148 lvc.pszText = szTemp;
149 ListView_InsertColumn(hListView, 2, &lvc);
150
151 lvc.iSubItem = 3;
152 lvc.cx = 80;
153 LoadString(hInstance, IDS_FOURTHCOLUMN, szTemp, 256);
154 lvc.pszText = szTemp;
155 ListView_InsertColumn(hListView, 3, &lvc);
156
157 lvc.iSubItem = 4;
158 lvc.cx = 100;
159 LoadString(hInstance, IDS_FITHCOLUMN, szTemp, 256);
160 lvc.pszText = szTemp;
161 ListView_InsertColumn(hListView, 4, &lvc);
162
163
164
165 /* ======================== Create Status Bar ============================== */
166
167 hStatus = CreateWindowEx(0,
168 STATUSCLASSNAME,
169 NULL,
170 WS_CHILD | WS_VISIBLE | SBARS_SIZEGRIP,
171 0, 0, 0, 0,
172 hwnd,
173 (HMENU)IDC_STATUSBAR,
174 hInstance,
175 NULL);
176 if(hStatus == NULL)
177 MessageBox(hwnd, _T("Could not create status bar."),
178 _T("Error!"), MB_OK | MB_ICONERROR);
179
180 SendMessage(hStatus, SB_SETPARTS, sizeof(statwidths)/sizeof(int), (LPARAM)statwidths);
181
182 /* populate the list view with all services */
183 if (! RefreshServiceList() )
184 GetError();
185
186 }
187 break;
188 case WM_SIZE:
189 {
190 RECT rcTool;
191 int iToolHeight;
192
193 RECT rcStatus;
194 int iStatusHeight;
195
196 int lvHeight;
197 RECT rcClient;
198
199 /* Size toolbar and get height */
200 hTool = GetDlgItem(hwnd, IDC_TOOLBAR);
201 SendMessage(hTool, TB_AUTOSIZE, 0, 0);
202
203 GetWindowRect(hTool, &rcTool);
204 iToolHeight = rcTool.bottom - rcTool.top;
205
206 /* Size status bar and get height */
207 hStatus = GetDlgItem(hwnd, IDC_STATUSBAR);
208 SendMessage(hStatus, WM_SIZE, 0, 0);
209
210 GetWindowRect(hStatus, &rcStatus);
211 iStatusHeight = rcStatus.bottom - rcStatus.top;
212
213 /* Calculate remaining height and size list view */
214 GetClientRect(hwnd, &rcClient);
215
216 lvHeight = rcClient.bottom - iToolHeight - iStatusHeight;
217
218 hListView = GetDlgItem(hwnd, IDC_SERVLIST);
219 SetWindowPos(hListView, NULL, 0, iToolHeight, rcClient.right, lvHeight, SWP_NOZORDER);
220 }
221 break;
222
223 case WM_NOTIFY:
224 {
225 LPNMITEMACTIVATE item;
226
227 switch (((LPNMHDR) lParam)->code)
228 {
229
230 case NM_DBLCLK:
231 item = (LPNMITEMACTIVATE) lParam;
232 PropSheets(hwnd);
233
234 break;
235
236 case TTN_GETDISPINFO:
237 {
238 LPTOOLTIPTEXT lpttt;
239 UINT idButton;
240
241 lpttt = (LPTOOLTIPTEXT) lParam;
242 lpttt->hinst = hInstance;
243
244 // Specify the resource identifier of the descriptive
245 // text for the given button.
246 idButton = lpttt->hdr.idFrom;
247 switch (idButton)
248 {
249 case ID_PROP:
250 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_PROP);
251 break;
252
253 case ID_REFRESH:
254 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_REFRESH);
255 break;
256
257 case ID_EXPORT:
258 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_EXPORT);
259 break;
260
261 case ID_START:
262 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_START);
263 break;
264
265 case ID_STOP:
266 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_STOP);
267 break;
268
269 case ID_PAUSE:
270 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_PAUSE);
271 break;
272
273 case ID_RESTART:
274 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_RESTART);
275 break;
276
277 case ID_NEW:
278 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_NEW);
279 break;
280
281 case ID_HELP:
282 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_HELP);
283 break;
284
285 case ID_EXIT:
286 lpttt->lpszText = MAKEINTRESOURCE(IDS_TOOLTIP_EXIT);
287 break;
288
289 }
290 }
291 break;
292
293 default:
294 break;
295 }
296 }
297 break;
298
299 case WM_CLOSE:
300 /* free the service array */
301 FreeMemory();
302 DestroyWindow(hwnd);
303 break;
304
305 case WM_DESTROY:
306 PostQuitMessage(0);
307 break;
308
309 case WM_COMMAND:
310 switch(LOWORD(wParam))
311 {
312 case ID_FILE_EXIT:
313 PostMessage(hwnd, WM_CLOSE, 0, 0);
314 break;
315
316 case ID_START:
317 break;
318
319 case ID_STOP:
320 break;
321
322 case ID_PAUSE:
323 break;
324
325 case ID_RESUME:
326 break;
327
328 case ID_RESTART:
329 break;
330
331 case ID_REFRESH:
332 break;
333
334 case ID_PROP:
335 PropSheets(hwnd);
336 break;
337
338 case ID_VIEW_CUSTOMIZE:
339 break;
340
341 case ID_HELP_ABOUT:
342 DialogBox(hInstance,
343 MAKEINTRESOURCE(IDD_ABOUTBOX),
344 hwnd,
345 AboutDialogProc);
346 break;
347
348 case ID_EXPORT:
349 break;
350
351 }
352 break;
353
354 default:
355 return DefWindowProc(hwnd, msg, wParam, lParam);
356 }
357 return 0;
358 }
359
360
361 //#pragma warning(disable : 4100)
362 int WINAPI WinMain(HINSTANCE hThisInstance, HINSTANCE hPrevInstance,
363 LPSTR lpCmdLine, int nCmdShow)
364 {
365 WNDCLASSEX wc;
366 MSG Msg;
367 BOOL bRet;
368
369 hInstance = hThisInstance;
370
371 InitCommonControls();
372
373 wc.cbSize = sizeof(WNDCLASSEX);
374 wc.style = 0;
375 wc.lpfnWndProc = WndProc;
376 wc.cbClsExtra = 0;
377 wc.cbWndExtra = 0;
378 wc.hInstance = hInstance;
379 wc.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_SM_ICON));
380 wc.hCursor = LoadCursor(NULL, IDC_ARROW);
381 wc.hbrBackground = (HBRUSH)(COLOR_BTNFACE + 1);
382 wc.lpszMenuName = MAKEINTRESOURCE(IDR_MAINMENU);
383 wc.lpszClassName = ClassName;
384 wc.hIconSm = (HICON)LoadImage(hInstance,
385 MAKEINTRESOURCE(IDI_SM_ICON), IMAGE_ICON, 16, 16, 0);
386
387 if(!RegisterClassEx(&wc))
388 {
389 MessageBox(NULL, _T("Window Registration Failed!"), _T("Error!"),
390 MB_ICONEXCLAMATION | MB_OK);
391 return 0;
392 }
393
394 hMainWnd = CreateWindowEx(
395 0,
396 ClassName,
397 _T("ReactOS Service Manager"),
398 WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN,
399 CW_USEDEFAULT, CW_USEDEFAULT, 700, 500,
400 NULL, NULL, hInstance, NULL);
401
402 if(hMainWnd == NULL)
403 {
404 MessageBox(NULL, _T("Window Creation Failed!"), _T("Error!"),
405 MB_ICONEXCLAMATION | MB_OK);
406 return 0;
407 }
408
409 ShowWindow(hMainWnd, nCmdShow);
410 UpdateWindow(hMainWnd);
411
412 while( (bRet = GetMessage( &Msg, NULL, 0, 0 )) != 0)
413 {
414 if (bRet == -1)
415 {
416 /* handle the error and possibly exit */
417 }
418 else
419 {
420 TranslateMessage(&Msg);
421 DispatchMessage(&Msg);
422 }
423 }
424 return Msg.wParam;
425 }
426
427