source: trunk/src/comctl32/toolbar.cpp@ 2875

Last change on this file since 2875 was 2875, checked in by cbratschi, 26 years ago

C -> C++, WINE animate, treeview WM_VSCROLL fixed

File size: 131.1 KB
Line 
1/* $Id: toolbar.cpp,v 1.1 2000-02-23 17:09:48 cbratschi Exp $ */
2/*
3 * Toolbar control
4 *
5 * Copyright 1998,1999 Eric Kohl
6 * Copyright 1999 Achim Hasenmueller
7 * Copyright 1999 Christoph Bratschi
8 *
9 * TODO:
10 * - A little bug in TOOLBAR_DrawMasked()
11 * - Button wrapping (under construction).
12 * - Messages (under construction).
13 * - Notifications.
14 * - Fix TB_SETROWS.
15 * - Tooltip support (almost complete).
16 * - Unicode support (under construction).
17 * - Fix TOOLBAR_SetButtonInfo32A/W.
18 * - Drag & drop of buttons
19 *
20 * Testing:
21 * - Run tests using Waite Group Windows95 API Bible Volume 2.
22 * The second cdrom contains executables addstr.exe, btncount.exe,
23 * btnstate.exe, butstrsz.exe, chkbtn.exe, chngbmp.exe, customiz.exe,
24 * enablebtn.exe, getbmp.exe, getbtn.exe, getflags.exe, hidebtn.exe,
25 * indetbtn.exe, insbtn.exe, pressbtn.exe, setbtnsz.exe, setcmdid.exe,
26 * setparnt.exe, setrows.exe, toolwnd.exe.
27 * - Microsofts controlspy examples.
28 */
29
30/*
31 - Corel 20000212 level
32 - WINE 991212 level
33*/
34
35/* CB: Odin32/WINE bugs
36 - IMAGELIST_Draw draws a line too at the bottom of the bitmap (toolbar.exe)
37 imagelist uses default size values instead of real bitmap values
38*/
39
40#include <string.h>
41
42#include "winbase.h"
43#include "commctrl.h"
44#include "cache.h"
45#include "comctl32.h"
46#include "toolbar.h"
47
48#define SEPARATOR_WIDTH 8
49#define TOP_BORDER 2
50#define BOTTOM_BORDER 2
51
52#define TOOLBAR_GetInfoPtr(hwnd) ((TOOLBAR_INFO *)GetWindowLongA(hwnd,0))
53
54
55static void
56TOOLBAR_DrawFlatSeparator (LPRECT lpRect, HDC hdc)
57{
58 INT x = (lpRect->left + lpRect->right) / 2 - 1;
59 INT yBottom = lpRect->bottom - 3;
60 INT yTop = lpRect->top + 1;
61
62 SelectObject ( hdc, GetSysColorPen (COLOR_3DSHADOW));
63 MoveToEx (hdc, x, yBottom, NULL);
64 LineTo (hdc, x, yTop);
65 x++;
66 SelectObject ( hdc, GetSysColorPen (COLOR_3DHILIGHT));
67 MoveToEx (hdc, x, yBottom, NULL);
68 LineTo (hdc, x, yTop);
69}
70
71
72static void
73TOOLBAR_DrawString (TOOLBAR_INFO *infoPtr, TBUTTON_INFO *btnPtr,
74 HDC hdc, INT nState, DWORD dwStyle)
75{
76 RECT rcText = btnPtr->rect;
77 HFONT hOldFont;
78 INT nOldBkMode;
79 COLORREF clrOld;
80
81 /* draw text */
82 if ((btnPtr->iString > -1) && (btnPtr->iString < infoPtr->nNumStrings)) {
83 InflateRect (&rcText, -3, -3);
84 if (dwStyle & TBSTYLE_LIST) {
85 rcText.left += infoPtr->nBitmapWidth;
86 }
87 else {
88 rcText.top += infoPtr->nBitmapHeight;
89 }
90 if (nState & (TBSTATE_PRESSED | TBSTATE_CHECKED))
91 OffsetRect (&rcText, 1, 1);
92
93 hOldFont = SelectObject (hdc, infoPtr->hFont);
94 nOldBkMode = SetBkMode (hdc, TRANSPARENT);
95 if (!(nState & TBSTATE_ENABLED)) {
96 clrOld = SetTextColor (hdc, GetSysColor (COLOR_3DHILIGHT));
97 OffsetRect (&rcText, 1, 1);
98 DrawTextW (hdc, infoPtr->strings[btnPtr->iString], -1,
99 &rcText, infoPtr->dwDTFlags);
100 SetTextColor (hdc, GetSysColor (COLOR_3DSHADOW));
101 OffsetRect (&rcText, -1, -1);
102 DrawTextW (hdc, infoPtr->strings[btnPtr->iString], -1,
103 &rcText, infoPtr->dwDTFlags);
104 }
105 else if (nState & TBSTATE_INDETERMINATE) {
106 clrOld = SetTextColor (hdc, GetSysColor (COLOR_3DSHADOW));
107 DrawTextW (hdc, infoPtr->strings[btnPtr->iString], -1,
108 &rcText, infoPtr->dwDTFlags);
109 }
110 else {
111 clrOld = SetTextColor (hdc, GetSysColor (COLOR_BTNTEXT));
112 DrawTextW (hdc, infoPtr->strings[btnPtr->iString], -1,
113 &rcText, infoPtr->dwDTFlags);
114 }
115
116 SetTextColor (hdc, clrOld);
117 SelectObject (hdc, hOldFont);
118 if (nOldBkMode != TRANSPARENT)
119 SetBkMode (hdc, nOldBkMode);
120 }
121}
122
123
124static void
125TOOLBAR_DrawPattern (HDC hdc, LPRECT lpRect)
126{
127 HBRUSH hbr = SelectObject (hdc, GetPattern55AABrush ());
128 INT cx = lpRect->right - lpRect->left;
129 INT cy = lpRect->bottom - lpRect->top;
130 PatBlt (hdc, lpRect->left, lpRect->top, cx, cy, 0x00FA0089);
131 SelectObject (hdc, hbr);
132}
133
134
135static void
136TOOLBAR_DrawMasked (TOOLBAR_INFO *infoPtr, TBUTTON_INFO *btnPtr,
137 HDC hdc, INT x, INT y)
138{
139 /* FIXME: this function is a hack since it uses image list
140 internals directly */
141
142 HIMAGELIST himl = infoPtr->himlDef;
143 HBITMAP hbmMask;
144 HDC hdcImageList;
145 HDC hdcMask;
146
147 if (!himl)
148 return;
149
150 /* create new dc's */
151 hdcImageList = CreateCompatibleDC (0);
152 hdcMask = CreateCompatibleDC (0);
153
154 /* create new bitmap */
155 hbmMask = CreateBitmap (himl->cx, himl->cy, 1, 1, NULL);
156 SelectObject (hdcMask, hbmMask);
157
158 /* copy the mask bitmap */
159 SelectObject (hdcImageList, himl->hbmMask);
160 SetBkColor (hdcImageList, RGB(255, 255, 255));
161 SetTextColor (hdcImageList, RGB(0, 0, 0));
162 BitBlt (hdcMask, 0, 0, himl->cx, himl->cy,
163 hdcImageList, himl->cx * btnPtr->iBitmap, 0, SRCCOPY);
164
165#if 0
166 /* add white mask from image */
167 SelectObject (hdcImageList, himl->hbmImage);
168 SetBkColor (hdcImageList, RGB(0, 0, 0));
169 BitBlt (hdcMask, 0, 0, himl->cx, himl->cy,
170 hdcImageList, himl->cx * btnPtr->iBitmap, 0, MERGEPAINT);
171#endif
172
173 /* draw the new mask */
174 SelectObject (hdc, GetSysColorBrush (COLOR_3DHILIGHT));
175 BitBlt (hdc, x+1, y+1, himl->cx, himl->cy,
176 hdcMask, 0, 0, 0xB8074A);
177
178 SelectObject (hdc, GetSysColorBrush (COLOR_3DSHADOW));
179 BitBlt (hdc, x, y, himl->cx, himl->cy,
180 hdcMask, 0, 0, 0xB8074A);
181
182 DeleteObject (hbmMask);
183 DeleteDC (hdcMask);
184 DeleteDC (hdcImageList);
185}
186
187
188static void
189TOOLBAR_DrawButton (HWND hwnd, TBUTTON_INFO *btnPtr, HDC hdc)
190{
191 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
192 DWORD dwStyle = GetWindowLongA (hwnd, GWL_STYLE);
193 RECT rc;
194
195 if (btnPtr->fsState & TBSTATE_HIDDEN) return;
196
197 rc = btnPtr->rect;
198
199 /* separator */
200 if (btnPtr->fsStyle & TBSTYLE_SEP)
201 {
202 if ((dwStyle & TBSTYLE_FLAT) && (btnPtr->iBitmap == 0))
203 TOOLBAR_DrawFlatSeparator (&rc, hdc);
204 return;
205 }
206
207 /* disabled */
208 if (!(btnPtr->fsState & TBSTATE_ENABLED))
209 {
210 if (!(dwStyle & TBSTYLE_FLAT))
211 DrawEdge (hdc, &rc, EDGE_RAISED,
212 BF_SOFT | BF_RECT | BF_MIDDLE | BF_ADJUST);
213
214 if (infoPtr->himlDis)
215 ImageList_Draw (infoPtr->himlDis, btnPtr->iBitmap, hdc,
216 rc.left+1, rc.top+1, ILD_NORMAL);
217 else
218 TOOLBAR_DrawMasked (infoPtr, btnPtr, hdc, rc.left+1, rc.top+1);
219
220 TOOLBAR_DrawString (infoPtr, btnPtr, hdc, btnPtr->fsState, dwStyle);
221 return;
222 }
223
224 /* pressed TBSTYLE_BUTTON */
225 if (btnPtr->fsState & TBSTATE_PRESSED)
226 {
227 if (dwStyle & TBSTYLE_FLAT)
228 DrawEdge(hdc, &rc, BDR_SUNKENOUTER, BF_RECT | BF_MIDDLE | BF_ADJUST);
229 else
230 DrawEdge (hdc, &rc, EDGE_SUNKEN, BF_RECT | BF_MIDDLE | BF_ADJUST);
231 ImageList_Draw (infoPtr->himlDef, btnPtr->iBitmap, hdc,
232 rc.left+2, rc.top+2, ILD_NORMAL);
233 TOOLBAR_DrawString (infoPtr, btnPtr, hdc, btnPtr->fsState, dwStyle);
234 return;
235 }
236
237 /* checked TBSTYLE_CHECK*/
238 if ((btnPtr->fsStyle & TBSTYLE_CHECK) &&
239 (btnPtr->fsState & TBSTATE_CHECKED)) {
240 if (dwStyle & TBSTYLE_FLAT)
241 DrawEdge (hdc, &rc, BDR_SUNKENOUTER,
242 BF_RECT | BF_MIDDLE | BF_ADJUST);
243 else
244 DrawEdge (hdc, &rc, EDGE_SUNKEN,
245 BF_RECT | BF_MIDDLE | BF_ADJUST);
246
247 TOOLBAR_DrawPattern (hdc, &rc);
248
249 ImageList_Draw (infoPtr->himlDef, btnPtr->iBitmap, hdc,
250 rc.left+2, rc.top+2, ILD_NORMAL);
251
252 TOOLBAR_DrawString (infoPtr, btnPtr, hdc, btnPtr->fsState, dwStyle);
253 return;
254 }
255
256 /* indeterminate */
257 if (btnPtr->fsState & TBSTATE_INDETERMINATE)
258 {
259 DrawEdge (hdc, &rc, EDGE_RAISED,
260 BF_SOFT | BF_RECT | BF_MIDDLE | BF_ADJUST);
261
262 TOOLBAR_DrawPattern (hdc, &rc);
263 TOOLBAR_DrawMasked (infoPtr, btnPtr, hdc, rc.left+1, rc.top+1);
264 TOOLBAR_DrawString (infoPtr, btnPtr, hdc, btnPtr->fsState, dwStyle);
265 return;
266 }
267
268 /* normal state */
269 if (dwStyle & TBSTYLE_FLAT)
270 {
271 if(btnPtr->bHot)
272 DrawEdge (hdc, &rc, BDR_RAISEDINNER, BF_RECT | BF_MIDDLE);
273
274 if(btnPtr->bHot && infoPtr->himlHot)
275 ImageList_Draw (infoPtr->himlHot, btnPtr->iBitmap, hdc,
276 rc.left +2, rc.top +2, ILD_NORMAL);
277 else
278 ImageList_Draw (infoPtr->himlDef, btnPtr->iBitmap, hdc,
279 rc.left +2, rc.top +2, ILD_NORMAL);
280 } else
281 {
282 DrawEdge (hdc, &rc, EDGE_RAISED,
283 BF_SOFT | BF_RECT | BF_MIDDLE | BF_ADJUST);
284
285 ImageList_Draw (infoPtr->himlDef, btnPtr->iBitmap, hdc,
286 rc.left+1, rc.top+1, ILD_NORMAL);
287 }
288
289 TOOLBAR_DrawString (infoPtr, btnPtr, hdc, btnPtr->fsState, dwStyle);
290}
291
292
293static void
294TOOLBAR_Refresh (HWND hwnd, HDC hdc)
295{
296 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
297 TBUTTON_INFO *btnPtr;
298 INT i;
299
300 /* draw buttons */
301 btnPtr = infoPtr->buttons;
302 for (i = 0; i < infoPtr->nNumButtons; i++, btnPtr++)
303 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
304}
305
306
307static void
308TOOLBAR_CalcStrings (HWND hwnd, LPSIZE lpSize)
309{
310 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
311 TBUTTON_INFO *btnPtr;
312 INT i;
313 HDC hdc;
314 HFONT hOldFont;
315 SIZE sz;
316
317 lpSize->cx = 0;
318 lpSize->cy = 0;
319 hdc = GetDC (0);
320 hOldFont = SelectObject (hdc, infoPtr->hFont);
321
322 btnPtr = infoPtr->buttons;
323 for (i = 0; i < infoPtr->nNumButtons; i++, btnPtr++) {
324 if (!(btnPtr->fsState & TBSTATE_HIDDEN) &&
325 (btnPtr->iString > -1) &&
326 (btnPtr->iString < infoPtr->nNumStrings)) {
327 LPWSTR lpText = infoPtr->strings[btnPtr->iString];
328 GetTextExtentPoint32W (hdc, lpText, lstrlenW (lpText), &sz);
329 if (sz.cx > lpSize->cx)
330 lpSize->cx = sz.cx;
331 if (sz.cy > lpSize->cy)
332 lpSize->cy = sz.cy;
333 }
334 }
335
336 SelectObject (hdc, hOldFont);
337 ReleaseDC (0, hdc);
338
339// TRACE (toolbar, "string size %d x %d!\n", lpSize->cx, lpSize->cy);
340}
341
342/***********************************************************************
343* TOOLBAR_WrapToolbar
344*
345* This function walks through the buttons and seperators in the
346* toolbar, and sets the TBSTATE_WRAP flag only on those items where
347* wrapping should occur based on the width of the toolbar window.
348* It does *not* calculate button placement itself. That task
349* takes place in TOOLBAR_CalcToolbar. If the program wants to manage
350* the toolbar wrapping on it's own, it can use the TBSTYLE_WRAPPABLE
351* flag, and set the TBSTATE_WRAP flags manually on the appropriate items.
352*/
353
354static void
355TOOLBAR_WrapToolbar( HWND hwnd, DWORD dwStyle )
356{
357 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
358 TBUTTON_INFO *btnPtr;
359 INT x, cx, i, j;
360 RECT rc;
361 BOOL bWrap, bButtonWrap;
362
363 /* When the toolbar window style is not TBSTYLE_WRAPABLE, */
364 /* no layout is necessary. Applications may use this style */
365 /* to perform their own layout on the toolbar. */
366 if( !(dwStyle & TBSTYLE_WRAPABLE) )
367 return;
368
369 btnPtr = infoPtr->buttons;
370 x = infoPtr->nIndent;
371
372 GetClientRect( GetParent(hwnd), &rc );
373 infoPtr->nWidth = rc.right - rc.left;
374 bButtonWrap = FALSE;
375
376 for (i = 0; i < infoPtr->nNumButtons; i++ )
377 {
378 bWrap = FALSE;
379 btnPtr[i].fsState &= ~TBSTATE_WRAP;
380
381 if (btnPtr[i].fsState & TBSTATE_HIDDEN)
382 continue;
383
384 /* UNDOCUMENTED: If a separator has a non zero bitmap index, */
385 /* it is the actual width of the separator. This is used for */
386 /* custom controls in toolbars. */
387 if (btnPtr[i].fsStyle & TBSTYLE_SEP)
388 cx = (btnPtr[i].iBitmap > 0) ?
389 btnPtr[i].iBitmap : SEPARATOR_WIDTH;
390 else
391 cx = infoPtr->nButtonWidth;
392
393 /* Two or more adjacent separators form a separator group. */
394 /* The first separator in a group should be wrapped to the */
395 /* next row if the previous wrapping is on a button. */
396 if( bButtonWrap &&
397 (btnPtr[i].fsStyle & TBSTYLE_SEP) &&
398 (i + 1 < infoPtr->nNumButtons ) &&
399 (btnPtr[i + 1].fsStyle & TBSTYLE_SEP) )
400 {
401 btnPtr[i].fsState |= TBSTATE_WRAP;
402 x = infoPtr->nIndent;
403 i++;
404 bButtonWrap = FALSE;
405 continue;
406 }
407
408 /* The layout makes sure the bitmap is visible, but not the button. */
409 if ( x + cx - (infoPtr->nButtonWidth - infoPtr->nBitmapWidth) / 2
410 > infoPtr->nWidth )
411 {
412 BOOL bFound = FALSE;
413
414 /* If the current button is a separator and not hidden, */
415 /* go to the next until it reaches a non separator. */
416 /* Wrap the last separator if it is before a button. */
417 while( ( (btnPtr[i].fsStyle & TBSTYLE_SEP) ||
418 (btnPtr[i].fsState & TBSTATE_HIDDEN) ) &&
419 i < infoPtr->nNumButtons )
420 {
421 i++;
422 bFound = TRUE;
423 }
424
425 if( bFound && i < infoPtr->nNumButtons )
426 {
427 i--;
428 btnPtr[i].fsState |= TBSTATE_WRAP;
429 x = infoPtr->nIndent;
430 bButtonWrap = FALSE;
431 continue;
432 }
433 else if ( i >= infoPtr->nNumButtons)
434 break;
435
436 /* If the current button is not a separator, find the last */
437 /* separator and wrap it. */
438 for ( j = i - 1; j >= 0 && !(btnPtr[j].fsState & TBSTATE_WRAP); j--)
439 {
440 if ((btnPtr[j].fsStyle & TBSTYLE_SEP) &&
441 !(btnPtr[j].fsState & TBSTATE_HIDDEN))
442 {
443 bFound = TRUE;
444 i = j;
445 x = infoPtr->nIndent;
446 btnPtr[j].fsState |= TBSTATE_WRAP;
447 bButtonWrap = FALSE;
448 break;
449 }
450 }
451
452 /* If no separator available for wrapping, wrap one of */
453 /* non-hidden previous button. */
454 if (!bFound)
455 {
456 for ( j = i - 1;
457 j >= 0 && !(btnPtr[j].fsState & TBSTATE_WRAP); j--)
458 {
459 if (btnPtr[j].fsState & TBSTATE_HIDDEN)
460 continue;
461
462 bFound = TRUE;
463 i = j;
464 x = infoPtr->nIndent;
465 btnPtr[j].fsState |= TBSTATE_WRAP;
466 bButtonWrap = TRUE;
467 break;
468 }
469 }
470
471 /* If all above failed, wrap the current button. */
472 if (!bFound)
473 {
474 btnPtr[i].fsState |= TBSTATE_WRAP;
475 bFound = TRUE;
476 x = infoPtr->nIndent;
477 if (btnPtr[i].fsState & TBSTYLE_SEP )
478 bButtonWrap = FALSE;
479 else
480 bButtonWrap = TRUE;
481 }
482 }
483 else
484 x += cx;
485 }
486}
487
488/***********************************************************************
489* TOOLBAR_CalcToolbar
490*
491* This function calculates button and separator placement. It first
492* calculates the button sizes, gets the toolbar window width and then
493* calls TOOLBAR_WrapToolbar to determine which buttons we need to wrap
494* on. It assigns a new location to each item and sends this location to
495* the tooltip window if appropriate. Finally, it updates the rcBound
496* rect and calculates the new required toolbar window height.
497*/
498
499static void
500TOOLBAR_CalcToolbar (HWND hwnd)
501{
502 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr(hwnd);
503 DWORD dwStyle = GetWindowLongA(hwnd, GWL_STYLE);
504 TBUTTON_INFO *btnPtr;
505 INT i, nRows, nSepRows;
506 INT x, y, cx, cy;
507 SIZE sizeString;
508 RECT rc;
509 BOOL bWrap;
510
511 TOOLBAR_CalcStrings (hwnd, &sizeString);
512
513 if (dwStyle & TBSTYLE_LIST) {
514 infoPtr->nButtonHeight = max(infoPtr->nBitmapHeight, sizeString.cy) + 6;
515 infoPtr->nButtonWidth = infoPtr->nBitmapWidth + sizeString.cx + 6;
516 }
517 else {
518 if (sizeString.cy > 0)
519 infoPtr->nButtonHeight = sizeString.cy + infoPtr->nBitmapHeight + 6;
520 else if (infoPtr->nButtonHeight < infoPtr->nBitmapHeight + 6)
521 infoPtr->nButtonHeight = infoPtr->nBitmapHeight + 6;
522
523 if (sizeString.cx > infoPtr->nBitmapWidth)
524 infoPtr->nButtonWidth = sizeString.cx + 6;
525 else if (infoPtr->nButtonWidth < infoPtr->nBitmapWidth + 6)
526 infoPtr->nButtonWidth = infoPtr->nBitmapWidth + 6;
527 }
528
529 TOOLBAR_WrapToolbar( hwnd, dwStyle );
530
531 x = infoPtr->nIndent;
532 y = (dwStyle & TBSTYLE_FLAT) ? 0: TOP_BORDER;
533 cx = infoPtr->nButtonWidth;
534 cy = infoPtr->nButtonHeight;
535 nRows = nSepRows = 0;
536
537 infoPtr->rcBound.top = y;
538 infoPtr->rcBound.left = x;
539 infoPtr->rcBound.bottom = y + cy;
540 infoPtr->rcBound.right = x;
541
542 btnPtr = infoPtr->buttons;
543 GetClientRect( GetParent(hwnd), &rc );
544 infoPtr->nWidth = rc.right - rc.left;
545
546 for (i = 0; i < infoPtr->nNumButtons; i++, btnPtr++ )
547 {
548 bWrap = FALSE;
549 if (btnPtr->fsState & TBSTATE_HIDDEN)
550 {
551 SetRectEmpty (&btnPtr->rect);
552 continue;
553 }
554
555 /* UNDOCUMENTED: If a separator has a non zero bitmap index, */
556 /* it is the actual width of the separator. This is used for */
557 /* custom controls in toolbars. */
558 if (btnPtr->fsStyle & TBSTYLE_SEP)
559 cx = (btnPtr->iBitmap > 0) ?
560 btnPtr->iBitmap : SEPARATOR_WIDTH;
561 else
562 cx = infoPtr->nButtonWidth;
563
564 if (btnPtr->fsState & TBSTATE_WRAP )
565 bWrap = TRUE;
566
567 SetRect (&btnPtr->rect, x, y, x + cx, y + cy);
568
569 if (infoPtr->rcBound.left > x)
570 infoPtr->rcBound.left = x;
571 if (infoPtr->rcBound.right < x + cx)
572 infoPtr->rcBound.right = x + cx;
573 if (infoPtr->rcBound.bottom < y + cy)
574 infoPtr->rcBound.bottom = y + cy;
575
576 /* Set the toolTip only for non-hidden, non-separator button */
577 if (infoPtr->hwndToolTip && !(btnPtr->fsStyle & TBSTYLE_SEP))
578 {
579 TTTOOLINFOA ti;
580
581 ZeroMemory (&ti,sizeof(TTTOOLINFOA));
582 ti.cbSize = sizeof(TTTOOLINFOA);
583 ti.hwnd = hwnd;
584 ti.uId = btnPtr->idCommand;
585 ti.rect = btnPtr->rect;
586 SendMessageA(infoPtr->hwndToolTip,TTM_NEWTOOLRECTA,0,(LPARAM)&ti);
587 }
588
589 /* btnPtr->nRow is zero based. The space between the rows is */
590 /* also considered as a row. */
591 btnPtr->nRow = nRows + nSepRows;
592 if( bWrap )
593 {
594 if ( !(btnPtr->fsStyle & TBSTYLE_SEP) )
595 y += cy;
596 else
597 {
598 /* UNDOCUMENTED: If a separator has a non zero bitmap index, */
599 /* it is the actual width of the separator. This is used for */
600 /* custom controls in toolbars. */
601 y += cy + ( (btnPtr->iBitmap > 0 ) ?
602 btnPtr->iBitmap : SEPARATOR_WIDTH) * 2 /3;
603
604 /* nSepRows is used to calculate the extra height follwoing */
605 /* the last row. */
606 nSepRows++;
607 }
608 x = infoPtr->nIndent;
609 nRows++;
610 }
611 else
612 x += cx;
613 }
614
615 /* infoPtr->nRows is the number of rows on the toolbar */
616 infoPtr->nRows = nRows + nSepRows + 1;
617
618 /* nSepRows * (infoPtr->nBitmapHeight + 1) is the space following */
619 /* the last row. */
620 infoPtr->nHeight = TOP_BORDER + (nRows + 1) * infoPtr->nButtonHeight +
621 nSepRows * (SEPARATOR_WIDTH * 2 / 3) +
622 nSepRows * (infoPtr->nBitmapHeight + 1) +
623 BOTTOM_BORDER;
624// TRACE (toolbar, "toolbar height %d\n", infoPtr->nHeight);
625}
626
627
628static INT
629TOOLBAR_InternalHitTest (HWND hwnd, LPPOINT lpPt)
630{
631 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
632 TBUTTON_INFO *btnPtr;
633 INT i;
634
635 btnPtr = infoPtr->buttons;
636 for (i = 0; i < infoPtr->nNumButtons; i++, btnPtr++) {
637 if (btnPtr->fsState & TBSTATE_HIDDEN)
638 continue;
639
640 if (btnPtr->fsStyle & TBSTYLE_SEP) {
641 if (PtInRect (&btnPtr->rect, *lpPt)) {
642// TRACE (toolbar, " ON SEPARATOR %d!\n", i);
643 return -i;
644 }
645 }
646 else {
647 if (PtInRect (&btnPtr->rect, *lpPt)) {
648// TRACE (toolbar, " ON BUTTON %d!\n", i);
649 return i;
650 }
651 }
652 }
653
654// TRACE (toolbar, " NOWHERE!\n");
655 return -1;
656}
657
658
659static INT
660TOOLBAR_GetButtonIndex (TOOLBAR_INFO *infoPtr, INT idCommand)
661{
662 TBUTTON_INFO *btnPtr;
663 INT i;
664
665 btnPtr = infoPtr->buttons;
666 for (i = 0; i < infoPtr->nNumButtons; i++, btnPtr++) {
667 if (btnPtr->idCommand == idCommand) {
668// TRACE (toolbar, "command=%d index=%d\n", idCommand, i);
669 return i;
670 }
671 }
672// TRACE (toolbar, "no index found for command=%d\n", idCommand);
673 return -1;
674}
675
676
677static INT
678TOOLBAR_GetCheckedGroupButtonIndex (TOOLBAR_INFO *infoPtr, INT nIndex)
679{
680 TBUTTON_INFO *btnPtr;
681 INT nRunIndex;
682
683 if ((nIndex < 0) || (nIndex > infoPtr->nNumButtons))
684 return -1;
685
686 /* check index button */
687 btnPtr = &infoPtr->buttons[nIndex];
688 if ((btnPtr->fsStyle & TBSTYLE_CHECKGROUP) == TBSTYLE_CHECKGROUP) {
689 if (btnPtr->fsState & TBSTATE_CHECKED)
690 return nIndex;
691 }
692
693 /* check previous buttons */
694 nRunIndex = nIndex - 1;
695 while (nRunIndex >= 0) {
696 btnPtr = &infoPtr->buttons[nRunIndex];
697 if ((btnPtr->fsStyle & TBSTYLE_CHECKGROUP) == TBSTYLE_CHECKGROUP) {
698 if (btnPtr->fsState & TBSTATE_CHECKED)
699 return nRunIndex;
700 }
701 else
702 break;
703 nRunIndex--;
704 }
705
706 /* check next buttons */
707 nRunIndex = nIndex + 1;
708 while (nRunIndex < infoPtr->nNumButtons) {
709 btnPtr = &infoPtr->buttons[nRunIndex];
710 if ((btnPtr->fsStyle & TBSTYLE_CHECKGROUP) == TBSTYLE_CHECKGROUP) {
711 if (btnPtr->fsState & TBSTATE_CHECKED)
712 return nRunIndex;
713 }
714 else
715 break;
716 nRunIndex++;
717 }
718
719 return -1;
720}
721
722
723static VOID
724TOOLBAR_RelayEvent (HWND hwndTip, HWND hwndMsg, UINT uMsg,
725 WPARAM wParam, LPARAM lParam)
726{
727 MSG msg;
728
729 msg.hwnd = hwndMsg;
730 msg.message = uMsg;
731 msg.wParam = wParam;
732 msg.lParam = lParam;
733 msg.time = GetMessageTime();
734 msg.pt.x = LOWORD(GetMessagePos());
735 msg.pt.y = HIWORD(GetMessagePos());
736
737 SendMessageA(hwndTip,TTM_RELAYEVENT,0,(LPARAM)&msg);
738}
739
740static void TBCUSTOMIZE_GetToolNameA(TOOLBAR_INFO* infoPtr,TBUTTON_INFO* btnPtr,INT pos)
741{
742 if (btnPtr->iString > -1 && btnPtr->iString < infoPtr->nNumStrings)
743 {
744 if (!btnPtr->pszName) btnPtr->pszName = (WCHAR*)COMCTL32_Alloc(MAXTOOLNAME*sizeof(WCHAR));
745 lstrcpynW(btnPtr->pszName,infoPtr->strings[btnPtr->iString],MAXTOOLNAME*sizeof(WCHAR));
746
747 return;
748 }
749
750 if (btnPtr->fsStyle & TBSTYLE_SEP)
751 {
752 if (!btnPtr->pszName) btnPtr->pszName = (WCHAR*)COMCTL32_Alloc(MAXTOOLNAME*sizeof(WCHAR));
753 lstrcpyAtoW(btnPtr->pszName,"Separator");
754 } else
755 {
756 TBNOTIFYA tbNotify;
757
758 tbNotify.hdr.hwndFrom = infoPtr->hwndToolbar;
759 tbNotify.hdr.idFrom = GetWindowLongA(infoPtr->hwndToolbar,GWL_ID);
760 tbNotify.hdr.code = TBN_GETBUTTONINFOA;
761 tbNotify.iItem = pos;
762 tbNotify.tbButton = (TBBUTTON*)btnPtr;
763 tbNotify.cchText = MAXTOOLNAME;
764 tbNotify.pszText = (CHAR*)COMCTL32_Alloc(MAXTOOLNAME);
765 tbNotify.pszText[0] = 0;
766
767 if (!SendMessageA(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)tbNotify.hdr.idFrom,(LPARAM)&tbNotify))
768 { //CB: failed, try other methods
769 if (infoPtr->hwndToolTip)
770 { //try to get tool tip text
771 TTTOOLINFOA ti;
772
773 ZeroMemory (&ti,sizeof(ti));
774 ti.cbSize = sizeof(ti);
775 ti.hwnd = infoPtr->hwndToolbar;
776 ti.uId = btnPtr->idCommand;
777 ti.hinst = 0;
778 ti.lpszText = (CHAR*)COMCTL32_Alloc(INFOTIPSIZE);
779 ti.lpszText[0] = 0;
780
781 SendMessageA(infoPtr->hwndToolTip,TTM_GETTEXTA,0,(LPARAM)&ti);
782 if (ti.lpszText[0] != 0) lstrcpynA(tbNotify.pszText,ti.lpszText,MAXTOOLNAME);
783 else strcpy(tbNotify.pszText,"Button");
784
785 COMCTL32_Free(ti.lpszText);
786
787 } else strcpy(tbNotify.pszText,"Button");
788 }
789
790 if (!btnPtr->pszName) btnPtr->pszName = (WCHAR*)COMCTL32_Alloc(MAXTOOLNAME*sizeof(WCHAR));
791 lstrcpyAtoW(btnPtr->pszName,tbNotify.pszText);
792 COMCTL32_Free(tbNotify.pszText);
793 }
794}
795
796static void TBCUSTOMIZE_GetToolNameW(TOOLBAR_INFO* infoPtr,TBUTTON_INFO* btnPtr,INT pos)
797{
798 if (btnPtr->iString > -1 && btnPtr->iString < infoPtr->nNumStrings)
799 {
800 if (!btnPtr->pszName) btnPtr->pszName = (WCHAR*)COMCTL32_Alloc(MAXTOOLNAME*sizeof(WCHAR));
801 lstrcpynW(btnPtr->pszName,infoPtr->strings[btnPtr->iString],MAXTOOLNAME*sizeof(WCHAR));
802
803 return;
804 }
805
806 if (btnPtr->fsStyle & TBSTYLE_SEP)
807 {
808 if (!btnPtr->pszName) btnPtr->pszName = (WCHAR*)COMCTL32_Alloc(MAXTOOLNAME*sizeof(WCHAR));
809 lstrcpyAtoW(btnPtr->pszName,"Separator");
810 } else
811 {
812 TBNOTIFYW tbNotify;
813
814 if (!btnPtr->pszName) btnPtr->pszName = (WCHAR*)COMCTL32_Alloc(MAXTOOLNAME*sizeof(WCHAR));
815 btnPtr->pszName[0] = 0;
816
817 tbNotify.hdr.hwndFrom = infoPtr->hwndToolbar;
818 tbNotify.hdr.idFrom = GetWindowLongA(infoPtr->hwndToolbar,GWL_ID);
819 tbNotify.hdr.code = TBN_GETBUTTONINFOW;
820 tbNotify.iItem = pos;
821 tbNotify.tbButton = (TBBUTTON*)btnPtr;
822 tbNotify.cchText = MAXTOOLNAME;
823 tbNotify.pszText = btnPtr->pszName;
824
825 if (!SendMessageW(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)tbNotify.hdr.idFrom,(LPARAM)&tbNotify))
826 { //CB: failed, try other methods
827 if (infoPtr->hwndToolTip)
828 { //try to get tool tip text
829 TTTOOLINFOW ti;
830
831 ZeroMemory (&ti,sizeof(ti));
832 ti.cbSize = sizeof(ti);
833 ti.hwnd = infoPtr->hwndToolbar;
834 ti.uId = btnPtr->idCommand;
835 ti.hinst = 0;
836 ti.lpszText = (WCHAR*)COMCTL32_Alloc(INFOTIPSIZE*sizeof(WCHAR));
837 ti.lpszText[0] = 0;
838
839 SendMessageA(infoPtr->hwndToolTip,TTM_GETTEXTW,0,(LPARAM)&ti);
840 if (ti.lpszText[0] != 0) lstrcpynW(btnPtr->pszName,ti.lpszText,MAXTOOLNAME);
841 else lstrcpyAtoW(btnPtr->pszName,"Button");
842
843 COMCTL32_Free(ti.lpszText);
844
845 } else lstrcpyAtoW(btnPtr->pszName,"Button");
846 }
847 }
848}
849
850static VOID TBCUSTOMIZE_AvailSelChange(HWND hwnd);
851static VOID TBCUSTOMIZE_VisSelChange(HWND hwnd);
852
853static BOOL TBCUSTOMIZE_FillData(HWND hwnd,TOOLBAR_INFO* infoPtr)
854{
855 TBUTTON_INFO* btnPtr;
856 INT i;
857 INT leftCount = 0;
858 INT rightCount = 0;
859 INT nItem;
860
861 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,WM_SETREDRAW,FALSE,0);
862 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,WM_SETREDRAW,FALSE,0);
863 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_RESETCONTENT,0,0);
864 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_RESETCONTENT,0,0);
865
866 /* insert 'virtual' separator button into 'available buttons' list */
867 nItem = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_ADDSTRING,0,(LPARAM)"Separator");
868 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_SETITEMDATA,nItem,0);
869
870 /* copy all buttons and append them to the listboxes */
871 btnPtr = infoPtr->buttons;
872 for (i = 0; i < infoPtr->nNumButtons; i++, btnPtr++)
873 {
874 if (IsWindowUnicode(infoPtr->hwndNotify))
875 {
876 TBNOTIFYW tbNotify;
877
878 tbNotify.hdr.hwndFrom = infoPtr->hwndToolbar;
879 tbNotify.hdr.idFrom = GetWindowLongA(infoPtr->hwndToolbar,GWL_ID);
880 tbNotify.iItem = i;
881 tbNotify.tbButton = (TBBUTTON*)btnPtr;
882 tbNotify.cchText = 0;
883 tbNotify.pszText = NULL;
884
885 // send TBN_QUERYINSERT notification
886
887 tbNotify.hdr.code = TBN_QUERYINSERT;
888
889 if (!SendMessageW(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)tbNotify.hdr.idFrom,(LPARAM)&tbNotify)) continue;
890
891 // send TBN_QUERYDELETE notification
892
893 tbNotify.hdr.code = TBN_QUERYDELETE;
894
895 btnPtr->bDelete = (BOOL)SendMessageW(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)tbNotify.hdr.idFrom,(LPARAM)&tbNotify);
896
897 //get tool name
898
899 TBCUSTOMIZE_GetToolNameW(infoPtr,btnPtr,i);
900
901 } else
902 {
903 TBNOTIFYA tbNotify;
904
905 tbNotify.hdr.hwndFrom = infoPtr->hwndToolbar;
906 tbNotify.hdr.idFrom = GetWindowLongA(infoPtr->hwndToolbar,GWL_ID);
907 tbNotify.iItem = i;
908 tbNotify.tbButton = (TBBUTTON*)btnPtr;
909 tbNotify.cchText = 0;
910 tbNotify.pszText = NULL;
911
912 // send TBN_QUERYINSERT notification
913
914 tbNotify.hdr.code = TBN_QUERYINSERT;
915
916 if (!SendMessageA(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)tbNotify.hdr.idFrom,(LPARAM)&tbNotify)) continue;
917
918 // send TBN_QUERYDELETE notification
919
920 tbNotify.hdr.code = TBN_QUERYDELETE;
921
922 btnPtr->bDelete = (BOOL)SendMessageA(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)tbNotify.hdr.idFrom,(LPARAM)&tbNotify);
923
924 //get tool name
925
926 TBCUSTOMIZE_GetToolNameA(infoPtr,btnPtr,i);
927 }
928
929 if (btnPtr->fsState & TBSTATE_HIDDEN)
930 {
931 nItem = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_ADDSTRING,0,(LPARAM)"");
932 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_SETITEMDATA,nItem,btnPtr->nCustomID);
933 leftCount++;
934 } else
935 {
936 nItem = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_ADDSTRING,0,(LPARAM)"");
937 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETITEMDATA,nItem,btnPtr->nCustomID);
938 rightCount++;
939 }
940 }
941
942 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_SETCURSEL,0,0);
943 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETCURSEL,(rightCount > 0) ? 0:(WPARAM)-1,0);
944
945 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,WM_SETREDRAW,TRUE,0);
946 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,WM_SETREDRAW,TRUE,0);
947 InvalidateRect(GetDlgItem(hwnd,IDC_AVAILBTN_LBOX),NULL,TRUE);
948 InvalidateRect(GetDlgItem(hwnd,IDC_TOOLBARBTN_LBOX),NULL,TRUE);
949
950 if (leftCount == 0 && rightCount == 0) return FALSE;
951
952 TBCUSTOMIZE_AvailSelChange(hwnd);
953 TBCUSTOMIZE_VisSelChange(hwnd);
954
955 return TRUE;
956}
957
958static BOOL TBCUSTOMIZE_InitDialog(HWND hwnd,WPARAM wParam,LPARAM lParam)
959{
960 TOOLBAR_INFO* infoPtr;
961
962 infoPtr = (TOOLBAR_INFO*)lParam;
963 SetWindowLongA(hwnd,DWL_USER,(DWORD)infoPtr);
964
965 if (infoPtr)
966 {
967 INT x;
968
969 //custom ID: 1-nNumButtons, 0 == new separator
970 for (x = 0;x < infoPtr->nNumButtons;x++)
971 {
972 infoPtr->buttons[x].nCustomID = x+1;
973 infoPtr->buttons[x].pszName = NULL;
974 }
975 infoPtr->nMaxCustomID = infoPtr->nNumButtons;
976
977 //save tools
978 infoPtr->nNumOldButtons = infoPtr->nNumButtons;
979 infoPtr->oldButtons = (TBUTTON_INFO*)COMCTL32_Alloc(infoPtr->nNumOldButtons*sizeof(TBUTTON_INFO));
980 memcpy(&infoPtr->oldButtons[0],&infoPtr->buttons[0],infoPtr->nNumOldButtons*sizeof(TBUTTON_INFO));
981
982 if (!TBCUSTOMIZE_FillData(hwnd,infoPtr)) EndDialog(hwnd,FALSE);
983 }
984
985 return TRUE;
986}
987
988static BOOL TBCUSTOMIZE_Close(HWND hwnd,WPARAM wParam,LPARAM lParam)
989{
990 EndDialog(hwnd,FALSE);
991
992 return TRUE;
993}
994
995static VOID TBCUSTOMIZE_Reset(HWND hwnd)
996{
997 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
998 NMHDR nmhdr;
999 INT x;
1000
1001 //Send TBN_RESET
1002 nmhdr.hwndFrom = infoPtr->hwndToolbar;
1003 nmhdr.idFrom = GetWindowLongA(infoPtr->hwndToolbar,GWL_ID);
1004 nmhdr.code = TBN_RESET;
1005
1006 SendMessageA(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)nmhdr.idFrom,(LPARAM)&nmhdr);
1007
1008 for (x = 0;x < infoPtr->nNumOldButtons;x++) COMCTL32_Free(infoPtr->oldButtons[x].pszName);
1009
1010 //restore data
1011 if (infoPtr->nNumButtons != infoPtr->nNumOldButtons)
1012 {
1013 COMCTL32_Free(infoPtr->buttons);
1014 infoPtr->nNumButtons = infoPtr->nNumOldButtons;
1015 infoPtr->buttons = (TBUTTON_INFO*)COMCTL32_Alloc(infoPtr->nNumButtons*sizeof(TBUTTON_INFO));
1016 }
1017 memcpy(&infoPtr->buttons[0],&infoPtr->oldButtons[0],infoPtr->nNumButtons*sizeof(TBUTTON_INFO));
1018
1019 if (!TBCUSTOMIZE_FillData(hwnd,infoPtr)) EndDialog(hwnd,FALSE);
1020
1021 TOOLBAR_CalcToolbar(infoPtr->hwndToolbar);
1022 InvalidateRect(infoPtr->hwndToolbar,NULL,TRUE);
1023}
1024
1025static TBUTTON_INFO* TBCUSTOMIZE_GetBtnPtr(TOOLBAR_INFO* infoPtr,INT customID)
1026{
1027 INT x;
1028 TBUTTON_INFO* btnPtr = infoPtr->buttons;
1029
1030 if (customID == 0) return NULL;
1031
1032 for (x = 0;x < infoPtr->nNumButtons;btnPtr++)
1033 if (btnPtr->nCustomID == customID) return btnPtr;
1034
1035 return NULL;
1036}
1037
1038static VOID TBCUSTOMIZE_AddTool(HWND hwnd)
1039{
1040 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
1041 LRESULT pos,count;
1042 INT customID;
1043 TBUTTON_INFO* btnPtr;
1044 LRESULT rightSel,rightCount,rightPos;
1045
1046 pos = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_GETCURSEL,0,0);
1047 if (pos == (LRESULT)-1) return;
1048
1049 count = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_GETCOUNT,0,0);
1050
1051 customID = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_GETITEMDATA,pos,0);
1052 if (customID == 0) btnPtr = NULL; else
1053 {
1054 btnPtr = TBCUSTOMIZE_GetBtnPtr(infoPtr,customID);
1055 if (btnPtr == NULL) return;
1056
1057 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_DELETESTRING,pos,0);
1058 }
1059
1060 rightSel = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETCURSEL,0,0);
1061 rightCount = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETCOUNT,0,0);
1062
1063 if (rightSel != (LRESULT)-1)
1064 rightPos = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_INSERTSTRING,rightSel,(LPARAM)"");
1065 else
1066 rightPos = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_ADDSTRING,0,(LPARAM)"");
1067 if (!btnPtr)
1068 { //new separator
1069 TBUTTON_INFO* newButtons;
1070
1071 newButtons = (TBUTTON_INFO*)COMCTL32_Alloc((infoPtr->nNumButtons+1)*sizeof(TBUTTON_INFO));
1072 memcpy(&newButtons[0],&infoPtr->buttons[0],infoPtr->nNumButtons*sizeof(TBUTTON_INFO));
1073 COMCTL32_Free(infoPtr->buttons);
1074
1075 infoPtr->buttons = newButtons;
1076 infoPtr->nNumButtons++;
1077
1078 btnPtr = &infoPtr->buttons[infoPtr->nNumButtons-1];
1079 ZeroMemory(btnPtr,sizeof(TBUTTON_INFO));
1080 btnPtr->fsStyle = TBSTYLE_SEP;
1081 btnPtr->bDelete = TRUE;
1082
1083 customID = ++infoPtr->nMaxCustomID;
1084 btnPtr->nCustomID = customID;
1085 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETITEMDATA,rightPos,customID);
1086 } else
1087 {
1088 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETITEMDATA,rightPos,customID);
1089 btnPtr->fsState &= ~TBSTATE_HIDDEN;
1090 }
1091 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETCURSEL,rightPos,0);
1092 TBCUSTOMIZE_VisSelChange(hwnd);
1093
1094 if (rightCount > 0)
1095 { //change order
1096 TBUTTON_INFO* btnPtr2;
1097 INT customID2,pos1,pos2;
1098
1099 pos1 = 0;
1100 while (infoPtr->buttons[pos1].nCustomID != customID) pos1++;
1101 if (rightPos < rightCount)
1102 { //insert before
1103 customID2 = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETITEMDATA,rightPos+1,0);
1104 pos2 = 0;
1105 while (infoPtr->buttons[pos2].nCustomID != customID2) pos2++;
1106 } else
1107 { //insert behind
1108 INT x;
1109
1110 customID2 = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETITEMDATA,rightPos-1,0);
1111 pos2 = 0;
1112 while (infoPtr->buttons[pos2].nCustomID != customID2) pos2++;
1113 //exchange to use first alogrithm
1114 x = pos1;
1115 pos1 = pos2;
1116 pos2 = x;
1117 }
1118
1119 if (pos1+1 != pos2)
1120 {
1121 TBUTTON_INFO temp;
1122 INT x;
1123
1124 memcpy(&temp,&infoPtr->buttons[pos1],sizeof(TBUTTON_INFO));
1125 if (pos1 < pos2)
1126 {
1127 for (x = pos1;x < pos2;x++)
1128 memcpy(&infoPtr->buttons[x],&infoPtr->buttons[x+1],sizeof(TBUTTON_INFO));
1129 memcpy(&infoPtr->buttons[pos2-1],&temp,sizeof(TBUTTON_INFO));
1130 } else
1131 {
1132 for (x = pos1-1;x >= pos2;x--)
1133 memcpy(&infoPtr->buttons[x+1],&infoPtr->buttons[x],sizeof(TBUTTON_INFO));
1134 memcpy(&infoPtr->buttons[pos2],&temp,sizeof(TBUTTON_INFO));
1135 }
1136 }
1137 }
1138
1139 if (pos == count-1 && pos > 0) pos--;
1140 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_SETCURSEL,pos,0);
1141 TBCUSTOMIZE_AvailSelChange(hwnd);
1142
1143 TOOLBAR_CalcToolbar(infoPtr->hwndToolbar);
1144 InvalidateRect(infoPtr->hwndToolbar,NULL,TRUE);
1145}
1146
1147static VOID TBCUSTOMIZE_RemoveTool(HWND hwnd)
1148{
1149 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
1150 LRESULT pos,count;
1151 INT customID;
1152 TBUTTON_INFO* btnPtr;
1153
1154 pos = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETCURSEL,0,0);
1155 if (pos == (LRESULT)-1) return;
1156
1157 count = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETCOUNT,0,0);
1158
1159 customID = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETITEMDATA,pos,0);
1160 if (customID == 0) return; //no allowed
1161
1162 btnPtr = TBCUSTOMIZE_GetBtnPtr(infoPtr,customID);
1163 if (btnPtr == NULL || !btnPtr->bDelete) return;
1164
1165 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_DELETESTRING,pos,0);
1166
1167 if (btnPtr->fsStyle & TBSTYLE_SEP)
1168 { //remove separator
1169 TBUTTON_INFO* newButtons;
1170 INT nIndex,x;
1171
1172 //find pos
1173 for (x = 0;x < infoPtr->nNumButtons;x++) if (&infoPtr->buttons[x] == btnPtr)
1174 {
1175 nIndex = x;
1176 break;
1177 }
1178
1179 infoPtr->nNumButtons--;
1180 newButtons = (TBUTTON_INFO*)COMCTL32_Alloc(infoPtr->nNumButtons*sizeof(TBUTTON_INFO));
1181
1182 if (nIndex > 0)
1183 memcpy(&newButtons[0],&infoPtr->buttons[0],nIndex*sizeof(TBUTTON_INFO));
1184
1185 if (nIndex < infoPtr->nNumButtons)
1186 memcpy (&newButtons[nIndex],&infoPtr->buttons[nIndex+1],(infoPtr->nNumButtons-nIndex)*sizeof(TBUTTON_INFO));
1187
1188 COMCTL32_Free(infoPtr->buttons);
1189 infoPtr->buttons = newButtons;
1190 } else
1191 {
1192 LRESULT leftSel,leftCount,leftPos;
1193
1194 leftSel = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_GETCURSEL,0,0);
1195 leftCount = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_GETCOUNT,0,0);
1196
1197 if (leftSel == 0)
1198 if (leftCount > 1) leftSel++; else leftSel = -1;
1199
1200 if (leftSel != (LRESULT)-1)
1201 leftPos = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_INSERTSTRING,leftSel,(LPARAM)"");
1202 else
1203 leftPos = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_ADDSTRING,0,(LPARAM)"");
1204 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_SETITEMDATA,leftPos,customID);
1205
1206 SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_SETCURSEL,leftPos,0);
1207 TBCUSTOMIZE_AvailSelChange(hwnd);
1208
1209 btnPtr->fsState |= TBSTATE_HIDDEN;
1210
1211 if (leftCount > 1)
1212 { //change order
1213 TBUTTON_INFO* btnPtr2;
1214 INT customID2,pos1,pos2;
1215
1216 pos1 = 0;
1217 while (infoPtr->buttons[pos1].nCustomID != customID) pos1++;
1218 if (leftPos < leftCount)
1219 { //insert before
1220 customID2 = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_GETITEMDATA,leftPos+1,0);
1221 pos2 = 0;
1222 while (infoPtr->buttons[pos2].nCustomID != customID2) pos2++;
1223 } else
1224 { //insert behind
1225 INT x;
1226
1227 customID2 = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_GETITEMDATA,leftPos-1,0);
1228 pos2 = 0;
1229 while (infoPtr->buttons[pos2].nCustomID != customID2) pos2++;
1230 //exchange to use first alogrithm
1231 x = pos1;
1232 pos1 = pos2;
1233 pos2 = x;
1234 }
1235
1236 if (pos1+1 != pos2)
1237 {
1238 TBUTTON_INFO temp;
1239 INT x;
1240
1241 memcpy(&temp,&infoPtr->buttons[pos1],sizeof(TBUTTON_INFO));
1242 if (pos1 < pos2)
1243 {
1244 for (x = pos1;x < pos2;x++)
1245 memcpy(&infoPtr->buttons[x],&infoPtr->buttons[x+1],sizeof(TBUTTON_INFO));
1246 memcpy(&infoPtr->buttons[pos2-1],&temp,sizeof(TBUTTON_INFO));
1247 } else
1248 {
1249 for (x = pos1-1;x >= pos2;x--)
1250 memcpy(&infoPtr->buttons[x+1],&infoPtr->buttons[x],sizeof(TBUTTON_INFO));
1251 memcpy(&infoPtr->buttons[pos2],&temp,sizeof(TBUTTON_INFO));
1252 }
1253 }
1254 }
1255 }
1256
1257 if (pos == count-1) pos--;
1258 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETCURSEL,pos,0);
1259 TBCUSTOMIZE_VisSelChange(hwnd);
1260
1261 TOOLBAR_CalcToolbar(infoPtr->hwndToolbar);
1262 InvalidateRect(infoPtr->hwndToolbar,NULL,TRUE);
1263}
1264
1265static VOID TBCUSTOMIZE_Help(HWND hwnd)
1266{
1267 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
1268 NMHDR nmhdr;
1269
1270 //Send TBN_CUSTHELP
1271 nmhdr.hwndFrom = infoPtr->hwndToolbar;
1272 nmhdr.idFrom = GetWindowLongA(infoPtr->hwndToolbar,GWL_ID);
1273 nmhdr.code = TBN_CUSTHELP;
1274
1275 SendMessageA(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)nmhdr.idFrom,(LPARAM)&nmhdr);
1276}
1277
1278static VOID TBCUSTOMIZE_MoveToolUp(HWND hwnd)
1279{
1280 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
1281 LRESULT pos;
1282 TBUTTON_INFO button;
1283 INT customID;
1284 TBUTTON_INFO* btnPtr1,* btnPtr2;
1285
1286 pos = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETCURSEL,0,0);
1287 if (pos == (LRESULT)-1 || pos == 0) return;
1288
1289 //update listbox
1290
1291 customID = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETITEMDATA,pos,0);
1292 btnPtr1 = TBCUSTOMIZE_GetBtnPtr(infoPtr,customID);
1293 if (btnPtr1 == NULL) return;
1294
1295 customID = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETITEMDATA,pos-1,0);
1296 btnPtr2 = TBCUSTOMIZE_GetBtnPtr(infoPtr,customID);
1297 if (btnPtr2 == NULL) return;
1298
1299 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETITEMDATA,pos,btnPtr2->nCustomID);
1300 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETITEMDATA,pos-1,btnPtr1->nCustomID);
1301
1302 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETCURSEL,pos-1,0);
1303 TBCUSTOMIZE_VisSelChange(hwnd);
1304
1305 //update buttons
1306 memcpy(&button,btnPtr1,sizeof(TBUTTON_INFO));
1307 memcpy(btnPtr1,btnPtr2,sizeof(TBUTTON_INFO));
1308 memcpy(btnPtr2,&button,sizeof(TBUTTON_INFO));
1309
1310 TOOLBAR_CalcToolbar(infoPtr->hwndToolbar);
1311 InvalidateRect(infoPtr->hwndToolbar,NULL,TRUE);
1312}
1313
1314static VOID TBCUSTOMIZE_MoveToolDown(HWND hwnd)
1315{
1316 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
1317 LRESULT pos,count;
1318 TBUTTON_INFO button;
1319 INT customID;
1320 TBUTTON_INFO* btnPtr1,* btnPtr2;
1321
1322 pos = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETCURSEL,0,0);
1323 if (pos == (LRESULT)-1) return;
1324
1325 count = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETCOUNT,0,0);
1326 if (pos == count-1) return;
1327
1328 //update listbox
1329
1330 customID = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETITEMDATA,pos,0);
1331 btnPtr1 = TBCUSTOMIZE_GetBtnPtr(infoPtr,customID);
1332 if (btnPtr1 == NULL) return;
1333
1334 customID = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETITEMDATA,pos+1,0);
1335 btnPtr2 = TBCUSTOMIZE_GetBtnPtr(infoPtr,customID);
1336 if (btnPtr2 == NULL) return;
1337
1338 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETITEMDATA,pos,btnPtr2->nCustomID);
1339 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETITEMDATA,pos+1,btnPtr1->nCustomID);
1340
1341 SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_SETCURSEL,pos+1,0);
1342 TBCUSTOMIZE_VisSelChange(hwnd);
1343
1344 //update buttons
1345 memcpy(&button,btnPtr1,sizeof(TBUTTON_INFO));
1346 memcpy(btnPtr1,btnPtr2,sizeof(TBUTTON_INFO));
1347 memcpy(btnPtr2,&button,sizeof(TBUTTON_INFO));
1348
1349 TOOLBAR_CalcToolbar(infoPtr->hwndToolbar);
1350 InvalidateRect(infoPtr->hwndToolbar,NULL,TRUE);
1351}
1352
1353static VOID TBCUSTOMIZE_AvailSelChange(HWND hwnd)
1354{
1355 LRESULT pos;
1356 HWND hwndBtn;
1357
1358 pos = SendDlgItemMessageA(hwnd,IDC_AVAILBTN_LBOX,LB_GETCURSEL,0,0);
1359
1360 hwndBtn = GetDlgItem(hwnd,IDOK);
1361 EnableWindow(hwndBtn,(pos == (LRESULT)-1) ? FALSE:TRUE);
1362}
1363
1364static VOID TBCUSTOMIZE_VisSelChange(HWND hwnd)
1365{
1366 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
1367 LRESULT pos;
1368
1369 pos = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETCURSEL,0,0);
1370
1371 if (pos == (LRESULT)-1)
1372 {
1373 EnableWindow(GetDlgItem(hwnd,IDC_REMOVE_BTN),FALSE);
1374 EnableWindow(GetDlgItem(hwnd,IDC_MOVEUP_BTN),FALSE);
1375 EnableWindow(GetDlgItem(hwnd,IDC_MOVEDN_BTN),FALSE);
1376 } else
1377 {
1378 INT customID;
1379 TBUTTON_INFO* btnPtr;
1380 LRESULT count;
1381
1382 customID = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETITEMDATA,pos,0);
1383 btnPtr = TBCUSTOMIZE_GetBtnPtr(infoPtr,customID);
1384 count = SendDlgItemMessageA(hwnd,IDC_TOOLBARBTN_LBOX,LB_GETCOUNT,0,0);
1385
1386 if (btnPtr)
1387 EnableWindow(GetDlgItem(hwnd,IDC_REMOVE_BTN),btnPtr->bDelete);
1388 else
1389 EnableWindow(GetDlgItem(hwnd,IDC_REMOVE_BTN),TRUE);
1390 EnableWindow(GetDlgItem(hwnd,IDC_MOVEUP_BTN),!(pos == 0));
1391 EnableWindow(GetDlgItem(hwnd,IDC_MOVEDN_BTN),!(pos == count-1));
1392 }
1393}
1394
1395static BOOL TBCUSTOMIZE_Command(HWND hwnd,WPARAM wParam,LPARAM lParam)
1396{
1397 switch(LOWORD(wParam))
1398 {
1399 case IDCANCEL:
1400 EndDialog(hwnd,FALSE);
1401 break;
1402 case IDC_RESET_BTN:
1403 TBCUSTOMIZE_Reset(hwnd);
1404 break;
1405 case IDOK: //== add tool
1406 TBCUSTOMIZE_AddTool(hwnd);
1407 break;
1408 case IDC_REMOVE_BTN:
1409 TBCUSTOMIZE_RemoveTool(hwnd);
1410 break;
1411 case IDC_HELP_BTN:
1412 TBCUSTOMIZE_Help(hwnd);
1413 break;
1414 case IDC_MOVEUP_BTN:
1415 TBCUSTOMIZE_MoveToolUp(hwnd);
1416 break;
1417 case IDC_MOVEDN_BTN:
1418 TBCUSTOMIZE_MoveToolDown(hwnd);
1419 break;
1420 case IDC_AVAILBTN_LBOX:
1421 switch(HIWORD(wParam))
1422 {
1423 case LBN_SELCHANGE:
1424 TBCUSTOMIZE_AvailSelChange(hwnd);
1425 break;
1426 case LBN_DBLCLK:
1427 TBCUSTOMIZE_AddTool(hwnd);
1428 break;
1429 }
1430 break;
1431 case IDC_TOOLBARBTN_LBOX:
1432 switch(HIWORD(wParam))
1433 {
1434 case LBN_SELCHANGE:
1435 TBCUSTOMIZE_VisSelChange(hwnd);
1436 break;
1437 case LBN_DBLCLK:
1438 TBCUSTOMIZE_RemoveTool(hwnd);
1439 break;
1440 }
1441 break;
1442 }
1443
1444 return TRUE;
1445}
1446
1447static BOOL TBCUSTOMIZE_Destroy(HWND hwnd,WPARAM wParam,LPARAM lParam)
1448{
1449 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
1450 INT x;
1451
1452 for (x = 0;x < infoPtr->nNumOldButtons;x++)
1453 COMCTL32_Free(infoPtr->oldButtons[x].pszName);
1454 COMCTL32_Free(infoPtr->oldButtons);
1455 infoPtr->oldButtons = NULL;
1456 infoPtr->nNumOldButtons = 0;
1457
1458 return TRUE;
1459}
1460
1461static BOOL TBCUSTOMIZE_DrawItem(HWND hwnd,WPARAM wParam,LPARAM lParam)
1462{
1463 if (wParam == IDC_AVAILBTN_LBOX || wParam == IDC_TOOLBARBTN_LBOX)
1464 {
1465 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
1466 LPDRAWITEMSTRUCT lpdis = (LPDRAWITEMSTRUCT)lParam;
1467 RECT rcButton;
1468 RECT rcText;
1469 HPEN hOldPen;
1470 HBRUSH hOldBrush;
1471 COLORREF oldText = 0;
1472 COLORREF oldBk = 0;
1473 INT customID;
1474 TBUTTON_INFO* btnPtr;
1475 DWORD dwStyle = GetWindowLongA(infoPtr->hwndToolbar,GWL_STYLE);
1476
1477 customID = SendDlgItemMessageA(hwnd,wParam,LB_GETITEMDATA,lpdis->itemID,0);
1478 btnPtr = TBCUSTOMIZE_GetBtnPtr(infoPtr,customID);
1479
1480 if (btnPtr != NULL && !btnPtr->bDelete)
1481 {
1482 if (lpdis->itemState & ODS_FOCUS) oldBk = SetBkColor(lpdis->hDC,GetSysColor(COLOR_HIGHLIGHT));
1483 oldText = SetTextColor(lpdis->hDC,GetSysColor(COLOR_GRAYTEXT));
1484 } else if (lpdis->itemState & ODS_FOCUS)
1485 {
1486 oldBk = SetBkColor (lpdis->hDC, GetSysColor(COLOR_HIGHLIGHT));
1487 oldText = SetTextColor (lpdis->hDC, GetSysColor(COLOR_HIGHLIGHTTEXT));
1488 }
1489
1490
1491 hOldPen = SelectObject (lpdis->hDC, GetSysColorPen ((lpdis->itemState & ODS_SELECTED)?COLOR_HIGHLIGHT:COLOR_WINDOW));
1492 hOldBrush = SelectObject (lpdis->hDC, GetSysColorBrush ((lpdis->itemState & ODS_FOCUS)?COLOR_HIGHLIGHT:COLOR_WINDOW));
1493
1494 /* fill background rectangle */
1495 Rectangle (lpdis->hDC,lpdis->rcItem.left,lpdis->rcItem.top,lpdis->rcItem.right,lpdis->rcItem.bottom);
1496
1497 /* calculate button and text rectangles */
1498 CopyRect (&rcButton, &lpdis->rcItem);
1499 InflateRect (&rcButton, -1, -1);
1500 CopyRect (&rcText, &rcButton);
1501 rcButton.right = rcButton.left + infoPtr->nBitmapWidth + 6;
1502 rcText.left = rcButton.right + 2;
1503
1504 /* draw focus rectangle */
1505 if (lpdis->itemState & ODS_FOCUS) DrawFocusRect (lpdis->hDC, &lpdis->rcItem);
1506
1507 //draw tool
1508 if (btnPtr && !(btnPtr->fsStyle & TBSTYLE_SEP))
1509 {
1510 //draw button
1511 if (dwStyle & TBSTYLE_FLAT)
1512 {
1513 ImageList_Draw(infoPtr->himlDef,btnPtr->iBitmap,lpdis->hDC,rcButton.left+2,rcButton.top+2,ILD_NORMAL);
1514 } else
1515 {
1516 DrawEdge (lpdis->hDC,&rcButton,EDGE_RAISED,BF_SOFT | BF_RECT | BF_MIDDLE | BF_ADJUST);
1517
1518 ImageList_Draw(infoPtr->himlDef,btnPtr->iBitmap,lpdis->hDC,rcButton.left+1,rcButton.top+1,ILD_NORMAL);
1519 }
1520
1521 } else
1522 { //draw separator
1523 if (!(dwStyle & TBSTYLE_FLAT))
1524 DrawEdge (lpdis->hDC,&rcButton,EDGE_RAISED,BF_SOFT | BF_RECT | BF_MIDDLE | BF_ADJUST);
1525
1526 TOOLBAR_DrawFlatSeparator(&rcButton,lpdis->hDC);
1527 }
1528
1529 /* draw text */
1530 if (!btnPtr || btnPtr->fsStyle & TBSTYLE_SEP)
1531 { //new separator
1532 DrawTextA(lpdis->hDC,"Separator",-1,&rcText,DT_LEFT | DT_VCENTER | DT_SINGLELINE);
1533 } else if (btnPtr->pszName != NULL)
1534 {
1535 DrawTextW(lpdis->hDC,btnPtr->pszName,-1,&rcText,DT_LEFT | DT_VCENTER | DT_SINGLELINE);
1536 }
1537
1538 if (lpdis->itemState & ODS_FOCUS)
1539 {
1540 SetBkColor (lpdis->hDC, oldBk);
1541 SetTextColor (lpdis->hDC, oldText);
1542 }
1543
1544 SelectObject (lpdis->hDC, hOldBrush);
1545 SelectObject (lpdis->hDC, hOldPen);
1546
1547 return TRUE;
1548 }
1549
1550 return FALSE;
1551}
1552
1553static BOOL TBCUSTOMIZE_MeasureItem(HWND hwnd,WPARAM wParam,LPARAM lParam)
1554{
1555 if (wParam == IDC_AVAILBTN_LBOX || wParam == IDC_TOOLBARBTN_LBOX)
1556 {
1557 TOOLBAR_INFO* infoPtr = (TOOLBAR_INFO*)GetWindowLongA(hwnd,DWL_USER);
1558 MEASUREITEMSTRUCT *lpmis = (MEASUREITEMSTRUCT*)lParam;
1559
1560 if (infoPtr)
1561 {
1562 DWORD dwStyle = GetWindowLongA(infoPtr->hwndToolbar,GWL_STYLE);
1563
1564 if (dwStyle & TBSTYLE_FLAT)
1565 lpmis->itemHeight = infoPtr->nBitmapHeight+4;
1566 else
1567 lpmis->itemHeight = infoPtr->nBitmapHeight+8;
1568 } else lpmis->itemHeight = 16+8;
1569
1570 return TRUE;
1571 }
1572
1573 return FALSE;
1574}
1575
1576/***********************************************************************
1577 * TOOLBAR_CustomizeDialogProc
1578 * This function implements the toolbar customization dialog.
1579 */
1580
1581/***********************************************************************
1582 * TOOLBAR_CustomizeDialogProc
1583 * This function implements the toolbar customization dialog.
1584 */
1585static BOOL WINAPI
1586TOOLBAR_CustomizeDialogProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
1587{
1588 TOOLBAR_INFO *infoPtr;
1589
1590 switch (uMsg)
1591 {
1592 case WM_INITDIALOG:
1593 return TBCUSTOMIZE_InitDialog(hwnd,wParam,lParam);
1594
1595 case WM_CLOSE:
1596 return TBCUSTOMIZE_Close(hwnd,wParam,lParam);
1597
1598 case WM_COMMAND:
1599 return TBCUSTOMIZE_Command(hwnd,wParam,lParam);
1600
1601 case WM_DESTROY:
1602 return TBCUSTOMIZE_Destroy(hwnd,wParam,lParam);
1603
1604 case WM_DRAWITEM:
1605 return TBCUSTOMIZE_DrawItem(hwnd,wParam,lParam);
1606
1607 case WM_MEASUREITEM:
1608 return TBCUSTOMIZE_MeasureItem(hwnd,wParam,lParam);
1609
1610 default:
1611 return FALSE;
1612 }
1613}
1614
1615//WINE version - not currently used
1616#if 0
1617static BOOL WINAPI
1618TOOLBAR_CustomizeDialogProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
1619{
1620 TOOLBAR_INFO *infoPtr = (TOOLBAR_INFO *)GetWindowLongA (hwnd, DWL_USER);
1621 static HDSA hDsa = NULL;
1622
1623 switch (uMsg)
1624 {
1625 case WM_INITDIALOG:
1626 infoPtr = (TOOLBAR_INFO *)lParam;
1627 SetWindowLongA (hwnd, DWL_USER, (DWORD)infoPtr);
1628
1629 hDsa = DSA_Create (sizeof(TBUTTON_INFO), 5);
1630
1631 if (infoPtr)
1632 {
1633 TBUTTON_INFO *btnPtr;
1634 INT i;
1635
1636 /* insert 'virtual' separator button into 'available buttons' list */
1637 SendDlgItemMessageA (hwnd, IDC_AVAILBTN_LBOX, LB_ADDSTRING, 0, (LPARAM)"");
1638
1639 /* copy all buttons and append them to the right listbox */
1640 btnPtr = infoPtr->buttons;
1641 for (i = 0; i < infoPtr->nNumButtons; i++, btnPtr++)
1642 {
1643 DSA_InsertItem (hDsa, i, btnPtr);
1644
1645 /* FIXME: hidden buttons appear in the 'toolbar buttons' list too */
1646 if (btnPtr->fsState & TBSTATE_HIDDEN)
1647 {
1648 SendDlgItemMessageA (hwnd, IDC_AVAILBTN_LBOX, LB_ADDSTRING, 0, (LPARAM)"");
1649 }
1650 else
1651 {
1652 SendDlgItemMessageA (hwnd, IDC_TOOLBARBTN_LBOX, LB_ADDSTRING, 0, (LPARAM)"");
1653 }
1654 }
1655
1656 /* append 'virtual' separator button to the 'toolbar buttons' list */
1657 /* TODO */
1658 }
1659 return TRUE;
1660
1661 case WM_CLOSE:
1662 EndDialog(hwnd, FALSE);
1663 return TRUE;
1664
1665 case WM_COMMAND:
1666 switch (LOWORD(wParam))
1667 {
1668 case IDCANCEL:
1669 EndDialog(hwnd, FALSE);
1670 break;
1671 }
1672 return TRUE;
1673
1674 case WM_DESTROY:
1675 if (hDsa)
1676 DSA_Destroy (hDsa);
1677 return TRUE;
1678
1679 case WM_DRAWITEM:
1680 if (wParam == IDC_AVAILBTN_LBOX || wParam == IDC_TOOLBARBTN_LBOX)
1681 {
1682 LPDRAWITEMSTRUCT lpdis = (LPDRAWITEMSTRUCT)lParam;
1683 TBUTTON_INFO btnPtr;
1684 RECT rcButton;
1685 RECT rcText;
1686 HPEN hOldPen;
1687 HBRUSH hOldBrush;
1688 COLORREF oldText = 0;
1689 COLORREF oldBk = 0;
1690
1691 FIXME("action: %x itemState: %x\n",
1692 lpdis->itemAction, lpdis->itemState);
1693
1694 DSA_GetItem (hDsa, 0 /*lpdis->itemID*/, &btnPtr);
1695
1696 if (lpdis->itemState & ODS_FOCUS)
1697 {
1698 oldBk = SetBkColor (lpdis->hDC, GetSysColor(COLOR_HIGHLIGHT));
1699 oldText = SetTextColor (lpdis->hDC, GetSysColor(COLOR_HIGHLIGHTTEXT));
1700 }
1701
1702 hOldPen = SelectObject (lpdis->hDC, GetSysColorPen ((lpdis->itemState & ODS_SELECTED)?COLOR_HIGHLIGHT:COLOR_WINDOW));
1703 hOldBrush = SelectObject (lpdis->hDC, GetSysColorBrush ((lpdis->itemState & ODS_FOCUS)?COLOR_HIGHLIGHT:COLOR_WINDOW));
1704
1705 /* fill background rectangle */
1706 Rectangle (lpdis->hDC, lpdis->rcItem.left, lpdis->rcItem.top,
1707 lpdis->rcItem.right, lpdis->rcItem.bottom);
1708
1709 /* calculate button and text rectangles */
1710 CopyRect (&rcButton, &lpdis->rcItem);
1711 InflateRect (&rcButton, -1, -1);
1712 CopyRect (&rcText, &rcButton);
1713 rcButton.right = rcButton.left + infoPtr->nBitmapWidth + 6;
1714 rcText.left = rcButton.right + 2;
1715
1716 /* draw focus rectangle */
1717 if (lpdis->itemState & ODS_FOCUS)
1718 DrawFocusRect (lpdis->hDC, &lpdis->rcItem);
1719
1720 /* draw button */
1721 DrawEdge (lpdis->hDC, &rcButton, EDGE_RAISED, BF_RECT|BF_MIDDLE|BF_SOFT);
1722
1723 /* draw image and text */
1724 if (wParam == IDC_AVAILBTN_LBOX && lpdis->itemID == 0)
1725 {
1726 /* virtual separator in the 'available' list */
1727 DrawTextA (lpdis->hDC, "Separator", -1, &rcText,
1728 DT_LEFT | DT_VCENTER | DT_SINGLELINE);
1729 }
1730 else
1731 {
1732 /* real button */
1733
1734 ImageList_Draw (infoPtr->himlDef, btnPtr.iBitmap, lpdis->hDC,
1735 rcButton.left+1, rcButton.top+1, ILD_NORMAL);
1736//AH: TODO: Find out why this happens!!!
1737if ((infoPtr->strings == NULL) || (infoPtr->strings[btnPtr.iString] == NULL))
1738 dprintf(("COMCTL32:TOOLBAR:CustomizeDialog - Error drawing string - pointer not found!\n"));
1739else
1740 DrawTextW (lpdis->hDC, infoPtr->strings[btnPtr.iString], -1, &rcText,
1741 DT_LEFT | DT_VCENTER | DT_SINGLELINE);
1742
1743 }
1744
1745 if (lpdis->itemState & ODS_FOCUS)
1746 {
1747 SetBkColor (lpdis->hDC, oldBk);
1748 SetTextColor (lpdis->hDC, oldText);
1749 }
1750
1751 SelectObject (lpdis->hDC, hOldBrush);
1752 SelectObject (lpdis->hDC, hOldPen);
1753
1754 return TRUE;
1755 }
1756 return FALSE;
1757
1758 case WM_MEASUREITEM:
1759 if (wParam == IDC_AVAILBTN_LBOX || wParam == IDC_TOOLBARBTN_LBOX)
1760 {
1761 MEASUREITEMSTRUCT *lpmis = (MEASUREITEMSTRUCT*)lParam;
1762
1763 if (infoPtr)
1764 lpmis->itemHeight = infoPtr->nBitmapHeight + 8;
1765 else
1766 lpmis->itemHeight = 16 + 8; /* default height */
1767
1768 return TRUE;
1769 }
1770 return FALSE;
1771
1772 default:
1773 return FALSE;
1774 }
1775}
1776#endif
1777
1778
1779/***********************************************************************
1780 * TOOLBAR_AddBitmap: Add the bitmaps to the default image list.
1781 *
1782 */
1783static LRESULT
1784TOOLBAR_AddBitmap (HWND hwnd, WPARAM wParam, LPARAM lParam)
1785{
1786 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
1787 LPTBADDBITMAP lpAddBmp = (LPTBADDBITMAP)lParam;
1788 INT nIndex = 0,nButtons;
1789 HBITMAP hbmLoad;
1790
1791 if (!lpAddBmp)
1792 return -1;
1793
1794 if (lpAddBmp->hInst == HINST_COMMCTRL)
1795 {
1796 if ((lpAddBmp->nID & ~1) == IDB_STD_SMALL_COLOR)
1797 nButtons = 15;
1798 else if ((lpAddBmp->nID & ~1) == IDB_VIEW_SMALL_COLOR)
1799 nButtons = 13;
1800 else if ((lpAddBmp->nID & ~1) == IDB_HIST_SMALL_COLOR)
1801 nButtons = 5;
1802 else
1803 return -1;
1804
1805// TRACE ("adding %d internal bitmaps!\n", nButtons);
1806
1807 /* Windows resize all the buttons to the size of a newly added standard Image*/
1808 if (lpAddBmp->nID & 1)
1809 {
1810 /* large icons */
1811 SendMessageA (hwnd, TB_SETBITMAPSIZE, 0,
1812 MAKELPARAM((WORD)26, (WORD)26));
1813 SendMessageA (hwnd, TB_SETBUTTONSIZE, 0,
1814 MAKELPARAM((WORD)33, (WORD)33));
1815 }
1816 else
1817 {
1818 /* small icons */
1819 SendMessageA (hwnd, TB_SETBITMAPSIZE, 0,
1820 MAKELPARAM((WORD)16, (WORD)16));
1821 SendMessageA (hwnd, TB_SETBUTTONSIZE, 0,
1822 MAKELPARAM((WORD)22, (WORD)22));
1823 }
1824
1825 TOOLBAR_CalcToolbar (hwnd);
1826 }
1827 else
1828 {
1829 nButtons = (INT)wParam;
1830 if (nButtons <= 0)
1831 return -1;
1832
1833// TRACE ("adding %d bitmaps!\n", nButtons);
1834 }
1835
1836 if (!(infoPtr->himlDef)) {
1837 /* create new default image list */
1838// TRACE ("creating default image list!\n");
1839
1840 infoPtr->himlDef =
1841 ImageList_Create (infoPtr->nBitmapWidth, infoPtr->nBitmapHeight,
1842 ILC_COLOR | ILC_MASK, nButtons, 2);
1843 infoPtr->himlInt = infoPtr->himlDef;
1844 }
1845
1846 /* Add bitmaps to the default image list */
1847 if (lpAddBmp->hInst == (HINSTANCE)0)
1848 {
1849 nIndex =
1850 ImageList_AddMasked (infoPtr->himlDef, (HBITMAP)lpAddBmp->nID,
1851 CLR_DEFAULT);
1852 }
1853 else if (lpAddBmp->hInst == HINST_COMMCTRL)
1854 {
1855 /* Add system bitmaps */
1856 switch (lpAddBmp->nID)
1857 {
1858 case IDB_STD_SMALL_COLOR:
1859 hbmLoad = LoadBitmapA (COMCTL32_hModule,
1860 MAKEINTRESOURCEA(IDB_STD_SMALL));
1861 nIndex = ImageList_AddMasked (infoPtr->himlDef,
1862 hbmLoad, CLR_DEFAULT);
1863 DeleteObject (hbmLoad);
1864 break;
1865
1866 case IDB_STD_LARGE_COLOR:
1867 hbmLoad = LoadBitmapA (COMCTL32_hModule,
1868 MAKEINTRESOURCEA(IDB_STD_LARGE));
1869 nIndex = ImageList_AddMasked (infoPtr->himlDef,
1870 hbmLoad, CLR_DEFAULT);
1871 DeleteObject (hbmLoad);
1872 break;
1873
1874 case IDB_VIEW_SMALL_COLOR:
1875 hbmLoad = LoadBitmapA (COMCTL32_hModule,
1876 MAKEINTRESOURCEA(IDB_VIEW_SMALL));
1877 nIndex = ImageList_AddMasked (infoPtr->himlDef,
1878 hbmLoad, CLR_DEFAULT);
1879 DeleteObject (hbmLoad);
1880 break;
1881
1882 case IDB_VIEW_LARGE_COLOR:
1883 hbmLoad = LoadBitmapA (COMCTL32_hModule,
1884 MAKEINTRESOURCEA(IDB_VIEW_LARGE));
1885 nIndex = ImageList_AddMasked (infoPtr->himlDef,
1886 hbmLoad, CLR_DEFAULT);
1887 DeleteObject (hbmLoad);
1888 break;
1889
1890 case IDB_HIST_SMALL_COLOR:
1891 hbmLoad = LoadBitmapA (COMCTL32_hModule,
1892 MAKEINTRESOURCEA(IDB_HIST_SMALL));
1893 nIndex = ImageList_AddMasked (infoPtr->himlDef,
1894 hbmLoad, CLR_DEFAULT);
1895 DeleteObject (hbmLoad);
1896 break;
1897
1898 case IDB_HIST_LARGE_COLOR:
1899 hbmLoad = LoadBitmapA (COMCTL32_hModule,
1900 MAKEINTRESOURCEA(IDB_HIST_LARGE));
1901 nIndex = ImageList_AddMasked (infoPtr->himlDef,
1902 hbmLoad, CLR_DEFAULT);
1903 DeleteObject (hbmLoad);
1904 break;
1905
1906 default:
1907 nIndex = ImageList_GetImageCount (infoPtr->himlDef);
1908 //ERR ("invalid imagelist!\n");
1909 break;
1910 }
1911 }
1912 else
1913 {
1914 hbmLoad = LoadBitmapA (lpAddBmp->hInst, (LPSTR)lpAddBmp->nID);
1915 nIndex = ImageList_AddMasked (infoPtr->himlDef, hbmLoad, CLR_DEFAULT);
1916 DeleteObject (hbmLoad);
1917 }
1918
1919 infoPtr->nNumBitmaps += nButtons;
1920
1921 return nIndex;
1922}
1923
1924
1925static LRESULT
1926TOOLBAR_AddButtonsA (HWND hwnd, WPARAM wParam, LPARAM lParam)
1927{
1928 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
1929 LPTBBUTTON lpTbb = (LPTBBUTTON)lParam;
1930 INT nOldButtons, nNewButtons, nAddButtons, nCount;
1931
1932// TRACE (toolbar, "adding %d buttons!\n", wParam);
1933
1934 nAddButtons = (UINT)wParam;
1935 nOldButtons = infoPtr->nNumButtons;
1936 nNewButtons = nOldButtons+nAddButtons;
1937
1938 if (infoPtr->nNumButtons == 0)
1939 {
1940 infoPtr->buttons = (TBUTTON_INFO*)COMCTL32_Alloc(sizeof(TBUTTON_INFO)*nNewButtons);
1941 } else
1942 {
1943 TBUTTON_INFO* oldButtons = infoPtr->buttons;
1944
1945 infoPtr->buttons = (TBUTTON_INFO*)COMCTL32_Alloc(sizeof(TBUTTON_INFO)*nNewButtons);
1946 memcpy(&infoPtr->buttons[0], &oldButtons[0],nOldButtons * sizeof(TBUTTON_INFO));
1947 COMCTL32_Free(oldButtons);
1948 }
1949
1950 infoPtr->nNumButtons = nNewButtons;
1951
1952 /* insert new button data */
1953 for (nCount = 0; nCount < nAddButtons; nCount++)
1954 {
1955 TBUTTON_INFO* btnPtr = &infoPtr->buttons[nOldButtons+nCount];
1956
1957 btnPtr->iBitmap = lpTbb[nCount].iBitmap;
1958 btnPtr->idCommand = lpTbb[nCount].idCommand;
1959 btnPtr->fsState = lpTbb[nCount].fsState;
1960 btnPtr->fsStyle = lpTbb[nCount].fsStyle;
1961 btnPtr->dwData = lpTbb[nCount].dwData;
1962 btnPtr->iString = lpTbb[nCount].iString;
1963 btnPtr->bHot = FALSE;
1964 btnPtr->bDelete = FALSE; //only used in customize
1965 btnPtr->pszName = NULL;
1966
1967 if ((infoPtr->hwndToolTip) && !(btnPtr->fsStyle & TBSTYLE_SEP))
1968 {
1969 TTTOOLINFOA ti;
1970
1971 ZeroMemory (&ti, sizeof(TTTOOLINFOA));
1972 ti.cbSize = sizeof (TTTOOLINFOA);
1973 ti.hwnd = hwnd;
1974 ti.uId = btnPtr->idCommand;
1975 ti.hinst = 0;
1976 ti.lpszText = LPSTR_TEXTCALLBACKA;
1977
1978 SendMessageA (infoPtr->hwndToolTip,TTM_ADDTOOLA,0,(LPARAM)&ti);
1979 }
1980 }
1981
1982 TOOLBAR_CalcToolbar(hwnd);
1983
1984 InvalidateRect(hwnd,NULL,FALSE);
1985
1986 return TRUE;
1987}
1988
1989static LRESULT
1990TOOLBAR_AddButtonsW (HWND hwnd, WPARAM wParam, LPARAM lParam)
1991{
1992 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
1993 LPTBBUTTON lpTbb = (LPTBBUTTON)lParam;
1994 INT nOldButtons, nNewButtons, nAddButtons, nCount;
1995
1996// TRACE("adding %d buttons!\n", wParam);
1997
1998 nAddButtons = (UINT)wParam;
1999 nOldButtons = infoPtr->nNumButtons;
2000 nNewButtons = nOldButtons + nAddButtons;
2001
2002 if (infoPtr->nNumButtons == 0) {
2003 infoPtr->buttons =
2004 (TBUTTON_INFO*)COMCTL32_Alloc (sizeof(TBUTTON_INFO) * nNewButtons);
2005 }
2006 else {
2007 TBUTTON_INFO *oldButtons = infoPtr->buttons;
2008 infoPtr->buttons =
2009 (TBUTTON_INFO*)COMCTL32_Alloc (sizeof(TBUTTON_INFO) * nNewButtons);
2010 memcpy (&infoPtr->buttons[0], &oldButtons[0],
2011 nOldButtons * sizeof(TBUTTON_INFO));
2012 COMCTL32_Free (oldButtons);
2013 }
2014
2015 infoPtr->nNumButtons = nNewButtons;
2016
2017 /* insert new button data */
2018 for (nCount = 0; nCount < nAddButtons; nCount++) {
2019 TBUTTON_INFO *btnPtr = &infoPtr->buttons[nOldButtons+nCount];
2020 btnPtr->iBitmap = lpTbb[nCount].iBitmap;
2021 btnPtr->idCommand = lpTbb[nCount].idCommand;
2022 btnPtr->fsState = lpTbb[nCount].fsState;
2023 btnPtr->fsStyle = lpTbb[nCount].fsStyle;
2024 btnPtr->dwData = lpTbb[nCount].dwData;
2025 btnPtr->iString = lpTbb[nCount].iString;
2026 btnPtr->bHot = FALSE;
2027
2028 if ((infoPtr->hwndToolTip) && !(btnPtr->fsStyle & TBSTYLE_SEP)) {
2029 TTTOOLINFOW ti;
2030
2031 ZeroMemory (&ti, sizeof(TTTOOLINFOW));
2032 ti.cbSize = sizeof (TTTOOLINFOW);
2033 ti.hwnd = hwnd;
2034 ti.uId = btnPtr->idCommand;
2035 ti.hinst = 0;
2036 ti.lpszText = LPSTR_TEXTCALLBACKW;
2037
2038 SendMessageW (infoPtr->hwndToolTip, TTM_ADDTOOLW,
2039 0, (LPARAM)&ti);
2040 }
2041 }
2042
2043 TOOLBAR_CalcToolbar (hwnd);
2044
2045 InvalidateRect(hwnd, NULL, FALSE);
2046
2047 return TRUE;
2048}
2049
2050
2051static LRESULT
2052TOOLBAR_AddStringA (HWND hwnd, WPARAM wParam, LPARAM lParam)
2053{
2054 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2055 INT nIndex;
2056
2057 if ((wParam) && (HIWORD(lParam) == 0)) {
2058 char szString[256];
2059 INT len;
2060// TRACE (toolbar, "adding string from resource!\n");
2061
2062 len = LoadStringA ((HINSTANCE)wParam, (UINT)lParam,
2063 szString, 256);
2064
2065// TRACE (toolbar, "len=%d \"%s\"\n", len, szString);
2066 nIndex = infoPtr->nNumStrings;
2067 if (infoPtr->nNumStrings == 0) {
2068 infoPtr->strings =
2069 (LPWSTR*)COMCTL32_Alloc (sizeof(LPWSTR));
2070 }
2071 else {
2072 LPWSTR *oldStrings = infoPtr->strings;
2073 infoPtr->strings =
2074 (LPWSTR*)COMCTL32_Alloc (sizeof(LPWSTR) * (infoPtr->nNumStrings + 1));
2075 memcpy (&infoPtr->strings[0], &oldStrings[0],
2076 sizeof(LPWSTR) * infoPtr->nNumStrings);
2077 COMCTL32_Free (oldStrings);
2078 }
2079
2080 infoPtr->strings[infoPtr->nNumStrings] =
2081 (WCHAR*)COMCTL32_Alloc (sizeof(WCHAR)*(len+1));
2082 lstrcpyAtoW (infoPtr->strings[infoPtr->nNumStrings], szString);
2083 infoPtr->nNumStrings++;
2084 }
2085 else {
2086 LPSTR p = (LPSTR)lParam;
2087 INT len;
2088
2089 if (p == NULL)
2090 return -1;
2091// TRACE (toolbar, "adding string(s) from array!\n");
2092 nIndex = infoPtr->nNumStrings;
2093 while (*p) {
2094 len = lstrlenA (p);
2095// TRACE (toolbar, "len=%d \"%s\"\n", len, p);
2096
2097 if (infoPtr->nNumStrings == 0) {
2098 infoPtr->strings =
2099 (LPWSTR*)COMCTL32_Alloc (sizeof(LPWSTR));
2100 }
2101 else {
2102 LPWSTR *oldStrings = infoPtr->strings;
2103 infoPtr->strings =
2104 (LPWSTR*)COMCTL32_Alloc (sizeof(LPWSTR) * (infoPtr->nNumStrings + 1));
2105 memcpy (&infoPtr->strings[0], &oldStrings[0],
2106 sizeof(LPWSTR) * infoPtr->nNumStrings);
2107 COMCTL32_Free (oldStrings);
2108 }
2109
2110 infoPtr->strings[infoPtr->nNumStrings] =
2111 (WCHAR*)COMCTL32_Alloc (sizeof(WCHAR)*(len+1));
2112 lstrcpyAtoW (infoPtr->strings[infoPtr->nNumStrings], p);
2113 infoPtr->nNumStrings++;
2114
2115 p += (len+1);
2116 }
2117 }
2118
2119 return nIndex;
2120}
2121
2122
2123static LRESULT
2124TOOLBAR_AddStringW (HWND hwnd, WPARAM wParam, LPARAM lParam)
2125{
2126 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2127 INT nIndex;
2128
2129 if ((wParam) && (HIWORD(lParam) == 0)) {
2130 WCHAR szString[256];
2131 INT len;
2132// TRACE (toolbar, "adding string from resource!\n");
2133
2134 len = LoadStringW ((HINSTANCE)wParam, (UINT)lParam,
2135 szString, 256);
2136
2137// TRACE (toolbar, "len=%d \"%s\"\n", len, debugstr_w(szString));
2138 nIndex = infoPtr->nNumStrings;
2139 if (infoPtr->nNumStrings == 0) {
2140 infoPtr->strings =
2141 (LPWSTR*)COMCTL32_Alloc (sizeof(LPWSTR));
2142 }
2143 else {
2144 LPWSTR *oldStrings = infoPtr->strings;
2145 infoPtr->strings =
2146 (LPWSTR*)COMCTL32_Alloc (sizeof(LPWSTR) * (infoPtr->nNumStrings + 1));
2147 memcpy (&infoPtr->strings[0], &oldStrings[0],
2148 sizeof(LPWSTR) * infoPtr->nNumStrings);
2149 COMCTL32_Free (oldStrings);
2150 }
2151
2152 infoPtr->strings[infoPtr->nNumStrings] =
2153 (WCHAR*)COMCTL32_Alloc (sizeof(WCHAR)*(len+1));
2154 lstrcpyW (infoPtr->strings[infoPtr->nNumStrings], szString);
2155 infoPtr->nNumStrings++;
2156 }
2157 else {
2158 LPWSTR p = (LPWSTR)lParam;
2159 INT len;
2160
2161 if (p == NULL)
2162 return -1;
2163// TRACE (toolbar, "adding string(s) from array!\n");
2164 nIndex = infoPtr->nNumStrings;
2165 while (*p) {
2166 len = lstrlenW (p);
2167// TRACE (toolbar, "len=%d \"%s\"\n", len, debugstr_w(p));
2168
2169 if (infoPtr->nNumStrings == 0) {
2170 infoPtr->strings =
2171 (LPWSTR*)COMCTL32_Alloc (sizeof(LPWSTR));
2172 }
2173 else {
2174 LPWSTR *oldStrings = infoPtr->strings;
2175 infoPtr->strings =
2176 (LPWSTR*)COMCTL32_Alloc (sizeof(LPWSTR) * (infoPtr->nNumStrings + 1));
2177 memcpy (&infoPtr->strings[0], &oldStrings[0],
2178 sizeof(LPWSTR) * infoPtr->nNumStrings);
2179 COMCTL32_Free (oldStrings);
2180 }
2181
2182 infoPtr->strings[infoPtr->nNumStrings] =
2183 (WCHAR*)COMCTL32_Alloc (sizeof(WCHAR)*(len+1));
2184 lstrcpyW (infoPtr->strings[infoPtr->nNumStrings], p);
2185 infoPtr->nNumStrings++;
2186
2187 p += (len+1);
2188 }
2189 }
2190
2191 return nIndex;
2192}
2193
2194
2195static LRESULT
2196TOOLBAR_AutoSize (HWND hwnd)
2197{
2198 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2199 DWORD dwStyle = GetWindowLongA (hwnd, GWL_STYLE);
2200 RECT parent_rect;
2201 HWND parent;
2202 INT x, y;
2203 INT cx, cy;
2204 UINT uPosFlags = 0;
2205
2206 //TRACE (toolbar, "resize forced!\n");
2207
2208 x = y = 0;
2209 parent = GetParent (hwnd);
2210 GetClientRect(parent, &parent_rect);
2211
2212 if (dwStyle & CCS_NORESIZE) {
2213 uPosFlags |= (SWP_NOSIZE | SWP_NOMOVE);
2214 cx = 0;
2215 cy = 0;
2216 }
2217 else {
2218 infoPtr->nWidth = parent_rect.right - parent_rect.left;
2219 TOOLBAR_CalcToolbar (hwnd);
2220 InvalidateRect( hwnd, NULL, TRUE );
2221 cy = infoPtr->nHeight;
2222 cx = infoPtr->nWidth;
2223 }
2224
2225 if (dwStyle & CCS_NOPARENTALIGN)
2226 uPosFlags |= SWP_NOMOVE;
2227
2228 if (!(dwStyle & CCS_NODIVIDER))
2229 cy += GetSystemMetrics(SM_CYEDGE);
2230
2231 if (dwStyle & WS_BORDER)
2232 {
2233 x = y = 1;
2234 cy += GetSystemMetrics(SM_CYEDGE);
2235 cx += GetSystemMetrics(SM_CYEDGE);
2236 }
2237
2238 infoPtr->bAutoSize = TRUE;
2239 SetWindowPos (hwnd, HWND_TOP, parent_rect.left - x, parent_rect.top - y,
2240 cx, cy, uPosFlags);
2241
2242 return 0;
2243}
2244
2245
2246static LRESULT
2247TOOLBAR_ButtonCount (HWND hwnd, WPARAM wParam, LPARAM lParam)
2248{
2249 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2250
2251 return infoPtr->nNumButtons;
2252}
2253
2254
2255static LRESULT
2256TOOLBAR_ButtonStructSize (HWND hwnd, WPARAM wParam, LPARAM lParam)
2257{
2258 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2259
2260 if (infoPtr == NULL) {
2261// ERR (toolbar, "(0x%x, 0x%x, 0x%lx)\n", hwnd, wParam, lParam);
2262// ERR (toolbar, "infoPtr == NULL!\n");
2263 return 0;
2264 }
2265
2266 infoPtr->dwStructSize = (DWORD)wParam;
2267
2268 return 0;
2269}
2270
2271
2272static LRESULT
2273TOOLBAR_ChangeBitmap (HWND hwnd, WPARAM wParam, LPARAM lParam)
2274{
2275 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2276 TBUTTON_INFO *btnPtr;
2277 HDC hdc;
2278 INT nIndex;
2279
2280 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2281 if (nIndex == -1)
2282 return FALSE;
2283
2284 btnPtr = &infoPtr->buttons[nIndex];
2285 btnPtr->iBitmap = LOWORD(lParam);
2286
2287 hdc = GetDC (hwnd);
2288 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
2289 ReleaseDC (hwnd, hdc);
2290
2291 return TRUE;
2292}
2293
2294
2295static LRESULT
2296TOOLBAR_CheckButton (HWND hwnd, WPARAM wParam, LPARAM lParam)
2297{
2298 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2299 TBUTTON_INFO *btnPtr;
2300 HDC hdc;
2301 INT nIndex;
2302 INT nOldIndex = -1;
2303 BOOL bChecked = FALSE;
2304
2305 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2306 if (nIndex == -1)
2307 return FALSE;
2308
2309 btnPtr = &infoPtr->buttons[nIndex];
2310
2311 if (!(btnPtr->fsStyle & TBSTYLE_CHECK))
2312 return FALSE;
2313
2314 bChecked = (btnPtr->fsState & TBSTATE_CHECKED) ? TRUE : FALSE;
2315
2316 if (LOWORD(lParam) == FALSE)
2317 btnPtr->fsState &= ~TBSTATE_CHECKED;
2318 else {
2319 if (btnPtr->fsStyle & TBSTYLE_GROUP) {
2320 nOldIndex =
2321 TOOLBAR_GetCheckedGroupButtonIndex (infoPtr, nIndex);
2322 if (nOldIndex == nIndex)
2323 return 0;
2324 if (nOldIndex != -1)
2325 infoPtr->buttons[nOldIndex].fsState &= ~TBSTATE_CHECKED;
2326 }
2327 btnPtr->fsState |= TBSTATE_CHECKED;
2328 }
2329
2330 if( bChecked != LOWORD(lParam) )
2331 {
2332 hdc = GetDC (hwnd);
2333 if (nOldIndex != -1)
2334 TOOLBAR_DrawButton (hwnd, &infoPtr->buttons[nOldIndex], hdc);
2335 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
2336 ReleaseDC (hwnd, hdc);
2337 }
2338
2339 /* FIXME: Send a WM_NOTIFY?? */
2340
2341 return TRUE;
2342}
2343
2344
2345static LRESULT
2346TOOLBAR_CommandToIndex (HWND hwnd, WPARAM wParam, LPARAM lParam)
2347{
2348 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2349
2350 return TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2351}
2352
2353static LRESULT
2354TOOLBAR_Customize (HWND hwnd)
2355{
2356 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2357 LRESULT ret;
2358 LPCVOID temp;
2359 HRSRC hRes;
2360 NMHDR nmhdr;
2361
2362 if (infoPtr->nNumButtons == 0) return 0;
2363
2364 /* send TBN_BEGINADJUST notification */
2365 nmhdr.hwndFrom = hwnd;
2366 nmhdr.idFrom = GetWindowLongA(hwnd,GWL_ID);
2367 nmhdr.code = TBN_BEGINADJUST;
2368
2369 SendMessageA (infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)nmhdr.idFrom,(LPARAM)&nmhdr);
2370
2371 if (!(hRes = FindResourceA (COMCTL32_hModule,
2372 MAKEINTRESOURCEA(IDD_TBCUSTOMIZE),
2373 RT_DIALOGA)))
2374 return FALSE;
2375
2376 if(!(temp = (LPVOID)LoadResource (COMCTL32_hModule, hRes)))
2377 return FALSE;
2378
2379 ret = DialogBoxIndirectParamA (GetWindowLongA (hwnd, GWL_HINSTANCE),
2380 (LPDLGTEMPLATEA)temp,
2381 hwnd,
2382 (DLGPROC)TOOLBAR_CustomizeDialogProc,
2383 (LPARAM)infoPtr);
2384
2385 /* send TBN_ENDADJUST notification */
2386 nmhdr.code = TBN_ENDADJUST;
2387
2388 SendMessageA(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)nmhdr.idFrom,(LPARAM)&nmhdr);
2389
2390 return ret;
2391}
2392
2393
2394static LRESULT
2395TOOLBAR_DeleteButton (HWND hwnd, WPARAM wParam, LPARAM lParam)
2396{
2397 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2398 INT nIndex = (INT)wParam;
2399
2400 if ((nIndex < 0) || (nIndex >= infoPtr->nNumButtons))
2401 return FALSE;
2402
2403 if ((infoPtr->hwndToolTip) &&
2404 !(infoPtr->buttons[nIndex].fsStyle & TBSTYLE_SEP)) {
2405 TTTOOLINFOA ti;
2406
2407 ZeroMemory (&ti, sizeof(TTTOOLINFOA));
2408 ti.cbSize = sizeof (TTTOOLINFOA);
2409 ti.hwnd = hwnd;
2410 ti.uId = infoPtr->buttons[nIndex].idCommand;
2411
2412 SendMessageA (infoPtr->hwndToolTip, TTM_DELTOOLA, 0, (LPARAM)&ti);
2413 }
2414
2415 COMCTL32_Free(infoPtr->buttons[nIndex].pszName);
2416
2417 if (infoPtr->nNumButtons == 1)
2418 {
2419// TRACE (toolbar, " simple delete!\n");
2420 COMCTL32_Free (infoPtr->buttons);
2421 infoPtr->buttons = NULL;
2422 infoPtr->nNumButtons = 0;
2423 } else
2424 {
2425 TBUTTON_INFO *oldButtons = infoPtr->buttons;
2426// TRACE(toolbar, "complex delete! [nIndex=%d]\n", nIndex);
2427
2428 infoPtr->nNumButtons--;
2429 infoPtr->buttons = (TBUTTON_INFO*)COMCTL32_Alloc (sizeof (TBUTTON_INFO) * infoPtr->nNumButtons);
2430 if (nIndex > 0) {
2431 memcpy (&infoPtr->buttons[0], &oldButtons[0],
2432 nIndex * sizeof(TBUTTON_INFO));
2433 }
2434
2435 if (nIndex < infoPtr->nNumButtons) {
2436 memcpy (&infoPtr->buttons[nIndex], &oldButtons[nIndex+1],
2437 (infoPtr->nNumButtons - nIndex) * sizeof(TBUTTON_INFO));
2438 }
2439
2440 COMCTL32_Free (oldButtons);
2441 }
2442
2443 TOOLBAR_CalcToolbar (hwnd);
2444
2445 InvalidateRect (hwnd, NULL, TRUE);
2446
2447 return TRUE;
2448}
2449
2450
2451static LRESULT
2452TOOLBAR_EnableButton (HWND hwnd, WPARAM wParam, LPARAM lParam)
2453{
2454 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2455 TBUTTON_INFO *btnPtr;
2456 HDC hdc;
2457 INT nIndex;
2458 BOOL bEnabled = FALSE;
2459
2460 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2461 if (nIndex == -1)
2462 return FALSE;
2463
2464 btnPtr = &infoPtr->buttons[nIndex];
2465 bEnabled = (btnPtr->fsState & TBSTATE_ENABLED )? TRUE : FALSE ;
2466
2467 if (LOWORD(lParam) == FALSE)
2468 btnPtr->fsState &= ~(TBSTATE_ENABLED | TBSTATE_PRESSED);
2469 else
2470 btnPtr->fsState |= TBSTATE_ENABLED;
2471
2472 if( bEnabled != LOWORD(lParam) )
2473 {
2474 hdc = GetDC (hwnd);
2475 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
2476 ReleaseDC (hwnd, hdc);
2477 }
2478
2479 return TRUE;
2480}
2481
2482
2483static LRESULT
2484TOOLBAR_GetAnchorHighlight (HWND hwnd)
2485{
2486 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2487
2488 return infoPtr->bAnchor;
2489}
2490
2491
2492static LRESULT
2493TOOLBAR_GetBitmap (HWND hwnd, WPARAM wParam, LPARAM lParam)
2494{
2495 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2496 INT nIndex;
2497
2498 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2499 if (nIndex == -1)
2500 return -1;
2501
2502 return infoPtr->buttons[nIndex].iBitmap;
2503}
2504
2505
2506static LRESULT
2507TOOLBAR_GetBitmapFlags (HWND hwnd, WPARAM wParam, LPARAM lParam)
2508{
2509 return (GetDeviceCaps (0, LOGPIXELSX) >= 120) ? TBBF_LARGE : 0;
2510}
2511
2512
2513static LRESULT
2514TOOLBAR_GetButton (HWND hwnd, WPARAM wParam, LPARAM lParam)
2515{
2516 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2517 LPTBBUTTON lpTbb = (LPTBBUTTON)lParam;
2518 INT nIndex = (INT)wParam;
2519 TBUTTON_INFO *btnPtr;
2520
2521 if (infoPtr == NULL)
2522 return FALSE;
2523
2524 if (lpTbb == NULL)
2525 return FALSE;
2526
2527 if ((nIndex < 0) || (nIndex >= infoPtr->nNumButtons))
2528 return FALSE;
2529
2530 btnPtr = &infoPtr->buttons[nIndex];
2531 lpTbb->iBitmap = btnPtr->iBitmap;
2532 lpTbb->idCommand = btnPtr->idCommand;
2533 lpTbb->fsState = btnPtr->fsState;
2534 lpTbb->fsStyle = btnPtr->fsStyle;
2535 lpTbb->dwData = btnPtr->dwData;
2536 lpTbb->iString = btnPtr->iString;
2537
2538 return TRUE;
2539}
2540
2541
2542static LRESULT
2543TOOLBAR_GetButtonInfoA (HWND hwnd, WPARAM wParam, LPARAM lParam)
2544{
2545 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2546 LPTBBUTTONINFOA lpTbInfo = (LPTBBUTTONINFOA)lParam;
2547 TBUTTON_INFO *btnPtr;
2548 INT nIndex;
2549
2550 if (infoPtr == NULL)
2551 return -1;
2552 if (lpTbInfo == NULL)
2553 return -1;
2554 if (lpTbInfo->cbSize < sizeof(TBBUTTONINFOA))
2555 return -1;
2556
2557 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2558 if (nIndex == -1)
2559 return -1;
2560
2561 btnPtr = &infoPtr->buttons[nIndex];
2562
2563 if (lpTbInfo->dwMask & TBIF_COMMAND)
2564 lpTbInfo->idCommand = btnPtr->idCommand;
2565 if (lpTbInfo->dwMask & TBIF_IMAGE)
2566 lpTbInfo->iImage = btnPtr->iBitmap;
2567 if (lpTbInfo->dwMask & TBIF_LPARAM)
2568 lpTbInfo->lParam = btnPtr->dwData;
2569 if (lpTbInfo->dwMask & TBIF_SIZE)
2570 lpTbInfo->cx = (WORD)(btnPtr->rect.right - btnPtr->rect.left);
2571 if (lpTbInfo->dwMask & TBIF_STATE)
2572 lpTbInfo->fsState = btnPtr->fsState;
2573 if (lpTbInfo->dwMask & TBIF_STYLE)
2574 lpTbInfo->fsStyle = btnPtr->fsStyle;
2575 if (lpTbInfo->dwMask & TBIF_TEXT) {
2576 if ((btnPtr->iString >= 0) || (btnPtr->iString < infoPtr->nNumStrings))
2577 lstrcpynWtoA (lpTbInfo->pszText,
2578 infoPtr->strings[btnPtr->iString],
2579 lpTbInfo->cchText);
2580 }
2581
2582 return nIndex;
2583}
2584
2585static LRESULT TOOLBAR_GetButtonInfoW(HWND hwnd,WPARAM wParam,LPARAM lParam)
2586{
2587 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2588 LPTBBUTTONINFOW lpTbInfo = (LPTBBUTTONINFOW)lParam;
2589 TBUTTON_INFO *btnPtr;
2590 INT nIndex;
2591
2592 if (infoPtr == NULL)
2593 return -1;
2594 if (lpTbInfo == NULL)
2595 return -1;
2596 if (lpTbInfo->cbSize < sizeof(TBBUTTONINFOW))
2597 return -1;
2598
2599 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2600 if (nIndex == -1)
2601 return -1;
2602
2603 btnPtr = &infoPtr->buttons[nIndex];
2604
2605 if (lpTbInfo->dwMask & TBIF_COMMAND)
2606 lpTbInfo->idCommand = btnPtr->idCommand;
2607 if (lpTbInfo->dwMask & TBIF_IMAGE)
2608 lpTbInfo->iImage = btnPtr->iBitmap;
2609 if (lpTbInfo->dwMask & TBIF_LPARAM)
2610 lpTbInfo->lParam = btnPtr->dwData;
2611 if (lpTbInfo->dwMask & TBIF_SIZE)
2612 lpTbInfo->cx = (WORD)(btnPtr->rect.right - btnPtr->rect.left);
2613 if (lpTbInfo->dwMask & TBIF_STATE)
2614 lpTbInfo->fsState = btnPtr->fsState;
2615 if (lpTbInfo->dwMask & TBIF_STYLE)
2616 lpTbInfo->fsStyle = btnPtr->fsStyle;
2617 if (lpTbInfo->dwMask & TBIF_TEXT) {
2618 if ((btnPtr->iString >= 0) || (btnPtr->iString < infoPtr->nNumStrings))
2619 lstrcpynW (lpTbInfo->pszText,
2620 infoPtr->strings[btnPtr->iString],
2621 lpTbInfo->cchText);
2622 }
2623
2624 return nIndex;
2625}
2626
2627
2628static LRESULT
2629TOOLBAR_GetButtonSize (HWND hwnd)
2630{
2631 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2632
2633 return MAKELONG((WORD)infoPtr->nButtonWidth,
2634 (WORD)infoPtr->nButtonHeight);
2635}
2636
2637
2638static LRESULT
2639TOOLBAR_GetButtonTextA (HWND hwnd, WPARAM wParam, LPARAM lParam)
2640{
2641 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2642 INT nIndex, nStringIndex;
2643
2644 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2645 if (nIndex == -1)
2646 return -1;
2647
2648 nStringIndex = infoPtr->buttons[nIndex].iString;
2649
2650// TRACE (toolbar, "index=%d stringIndex=%d\n", nIndex, nStringIndex);
2651
2652 if ((nStringIndex < 0) || (nStringIndex >= infoPtr->nNumStrings))
2653 return -1;
2654
2655 if (lParam == 0) return -1;
2656
2657 lstrcpyWtoA ((LPSTR)lParam, infoPtr->strings[nStringIndex]);
2658
2659 return lstrlenW (infoPtr->strings[nStringIndex]);
2660}
2661
2662static LRESULT TOOLBAR_GetButtonTextW (HWND hwnd, WPARAM wParam, LPARAM lParam)
2663{
2664 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2665 INT nIndex, nStringIndex;
2666
2667 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2668 if (nIndex == -1)
2669 return -1;
2670
2671 nStringIndex = infoPtr->buttons[nIndex].iString;
2672
2673// TRACE (toolbar, "index=%d stringIndex=%d\n", nIndex, nStringIndex);
2674
2675 if ((nStringIndex < 0) || (nStringIndex >= infoPtr->nNumStrings))
2676 return -1;
2677
2678 if (lParam == 0) return -1;
2679
2680 lstrcpyW ((LPWSTR)lParam, infoPtr->strings[nStringIndex]);
2681
2682 return lstrlenW (infoPtr->strings[nStringIndex]);
2683}
2684
2685/* << TOOLBAR_GetButtonText32W >> */
2686/* << TOOLBAR_GetColorScheme >> */
2687
2688
2689static LRESULT
2690TOOLBAR_GetDisabledImageList (HWND hwnd, WPARAM wParam, LPARAM lParam)
2691{
2692 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2693
2694 return (LRESULT)infoPtr->himlDis;
2695}
2696
2697
2698static LRESULT
2699TOOLBAR_GetExtendedStyle (HWND hwnd)
2700{
2701 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2702
2703 return infoPtr->dwExStyle;
2704}
2705
2706
2707static LRESULT
2708TOOLBAR_GetHotImageList (HWND hwnd, WPARAM wParam, LPARAM lParam)
2709{
2710 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2711
2712 return (LRESULT)infoPtr->himlHot;
2713}
2714
2715
2716static LRESULT
2717TOOLBAR_GetHotItem (HWND hwnd)
2718{
2719 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2720
2721 if (!(GetWindowLongA (hwnd, GWL_STYLE) & TBSTYLE_FLAT))
2722 return -1;
2723
2724 if (infoPtr->nHotItem < 0)
2725 return -1;
2726
2727 return (LRESULT)infoPtr->nHotItem;
2728}
2729
2730
2731static LRESULT
2732TOOLBAR_GetImageList (HWND hwnd, WPARAM wParam, LPARAM lParam)
2733{
2734 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2735
2736 return (LRESULT)infoPtr->himlDef;
2737}
2738
2739
2740/* << TOOLBAR_GetInsertMark >> */
2741/* << TOOLBAR_GetInsertMarkColor >> */
2742
2743
2744static LRESULT
2745TOOLBAR_GetItemRect (HWND hwnd, WPARAM wParam, LPARAM lParam)
2746{
2747 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2748 TBUTTON_INFO *btnPtr;
2749 LPRECT lpRect;
2750 INT nIndex;
2751
2752 if (infoPtr == NULL)
2753 return FALSE;
2754 nIndex = (INT)wParam;
2755 btnPtr = &infoPtr->buttons[nIndex];
2756 if ((nIndex < 0) || (nIndex >= infoPtr->nNumButtons))
2757 return FALSE;
2758 lpRect = (LPRECT)lParam;
2759 if (lpRect == NULL)
2760 return FALSE;
2761 if (btnPtr->fsState & TBSTATE_HIDDEN)
2762 return FALSE;
2763
2764 TOOLBAR_CalcToolbar( hwnd );
2765
2766 lpRect->left = btnPtr->rect.left;
2767 lpRect->right = btnPtr->rect.right;
2768 lpRect->bottom = btnPtr->rect.bottom;
2769 lpRect->top = btnPtr->rect.top;
2770
2771 return TRUE;
2772}
2773
2774
2775static LRESULT
2776TOOLBAR_GetMaxSize (HWND hwnd, WPARAM wParam, LPARAM lParam)
2777{
2778 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2779 LPSIZE lpSize = (LPSIZE)lParam;
2780
2781 if (lpSize == NULL)
2782 return FALSE;
2783
2784 lpSize->cx = infoPtr->rcBound.right - infoPtr->rcBound.left;
2785 lpSize->cy = infoPtr->rcBound.bottom - infoPtr->rcBound.top;
2786
2787// TRACE (toolbar, "maximum size %d x %d\n",
2788// infoPtr->rcBound.right - infoPtr->rcBound.left,
2789// infoPtr->rcBound.bottom - infoPtr->rcBound.top);
2790
2791 return TRUE;
2792}
2793
2794
2795/* << TOOLBAR_GetObject >> */
2796/* << TOOLBAR_GetPadding >> */
2797
2798
2799static LRESULT
2800TOOLBAR_GetRect (HWND hwnd, WPARAM wParam, LPARAM lParam)
2801{
2802 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2803 TBUTTON_INFO *btnPtr;
2804 LPRECT lpRect;
2805 INT nIndex;
2806
2807 if (infoPtr == NULL)
2808 return FALSE;
2809 nIndex = (INT)wParam;
2810 btnPtr = &infoPtr->buttons[nIndex];
2811 if ((nIndex < 0) || (nIndex >= infoPtr->nNumButtons))
2812 return FALSE;
2813 lpRect = (LPRECT)lParam;
2814 if (lpRect == NULL)
2815 return FALSE;
2816
2817 lpRect->left = btnPtr->rect.left;
2818 lpRect->right = btnPtr->rect.right;
2819 lpRect->bottom = btnPtr->rect.bottom;
2820 lpRect->top = btnPtr->rect.top;
2821
2822 return TRUE;
2823}
2824
2825
2826static LRESULT
2827TOOLBAR_GetRows (HWND hwnd, WPARAM wParam, LPARAM lParam)
2828{
2829 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2830
2831 if (GetWindowLongA (hwnd, GWL_STYLE) & TBSTYLE_WRAPABLE)
2832 return infoPtr->nRows;
2833 else
2834 return 1;
2835}
2836
2837
2838static LRESULT
2839TOOLBAR_GetState (HWND hwnd, WPARAM wParam, LPARAM lParam)
2840{
2841 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2842 INT nIndex;
2843
2844 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2845 if (nIndex == -1)
2846 return -1;
2847
2848 return infoPtr->buttons[nIndex].fsState;
2849}
2850
2851
2852static LRESULT
2853TOOLBAR_GetStyle (HWND hwnd, WPARAM wParam, LPARAM lParam)
2854{
2855 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2856 INT nIndex;
2857
2858 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2859 if (nIndex == -1)
2860 return -1;
2861
2862 return infoPtr->buttons[nIndex].fsStyle;
2863}
2864
2865
2866static LRESULT
2867TOOLBAR_GetTextRows (HWND hwnd, WPARAM wParam, LPARAM lParam)
2868{
2869 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2870
2871 if (infoPtr == NULL)
2872 return 0;
2873
2874 return infoPtr->nMaxTextRows;
2875}
2876
2877
2878static LRESULT
2879TOOLBAR_GetToolTips (HWND hwnd, WPARAM wParam, LPARAM lParam)
2880{
2881 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2882
2883 if (infoPtr == NULL) return 0;
2884 return infoPtr->hwndToolTip;
2885}
2886
2887
2888static LRESULT
2889TOOLBAR_GetUnicodeFormat (HWND hwnd, WPARAM wParam, LPARAM lParam)
2890{
2891 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2892
2893// TRACE (toolbar, "%s hwnd=0x%x stub!\n",
2894// infoPtr->bUnicode ? "TRUE" : "FALSE", hwnd);
2895
2896 return infoPtr->bUnicode;
2897}
2898
2899static LRESULT
2900TOOLBAR_GetVersion (HWND hwnd)
2901{
2902 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2903 return infoPtr->iVersion;
2904}
2905
2906static LRESULT
2907TOOLBAR_HideButton (HWND hwnd, WPARAM wParam, LPARAM lParam)
2908{
2909 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2910 TBUTTON_INFO *btnPtr;
2911 INT nIndex;
2912
2913 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2914 if (nIndex == -1)
2915 return FALSE;
2916
2917 btnPtr = &infoPtr->buttons[nIndex];
2918 if (LOWORD(lParam) == FALSE)
2919 btnPtr->fsState &= ~TBSTATE_HIDDEN;
2920 else
2921 btnPtr->fsState |= TBSTATE_HIDDEN;
2922
2923 TOOLBAR_CalcToolbar (hwnd);
2924
2925 InvalidateRect (hwnd, NULL, TRUE);
2926
2927 return TRUE;
2928}
2929
2930
2931static LRESULT
2932TOOLBAR_HitTest (HWND hwnd, WPARAM wParam, LPARAM lParam)
2933{
2934 return TOOLBAR_InternalHitTest (hwnd, (LPPOINT)lParam);
2935}
2936
2937
2938static LRESULT
2939TOOLBAR_Indeterminate (HWND hwnd, WPARAM wParam, LPARAM lParam)
2940{
2941 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2942 TBUTTON_INFO *btnPtr;
2943 HDC hdc;
2944 INT nIndex;
2945
2946 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
2947 if (nIndex == -1)
2948 return FALSE;
2949
2950 btnPtr = &infoPtr->buttons[nIndex];
2951 if (LOWORD(lParam) == FALSE)
2952 btnPtr->fsState &= ~TBSTATE_INDETERMINATE;
2953 else
2954 btnPtr->fsState |= TBSTATE_INDETERMINATE;
2955
2956 hdc = GetDC (hwnd);
2957 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
2958 ReleaseDC (hwnd, hdc);
2959
2960 return TRUE;
2961}
2962
2963
2964static LRESULT
2965TOOLBAR_InsertButtonA (HWND hwnd, WPARAM wParam, LPARAM lParam)
2966{
2967 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
2968 LPTBBUTTON lpTbb = (LPTBBUTTON)lParam;
2969 INT nIndex = (INT)wParam;
2970 TBUTTON_INFO *oldButtons;
2971
2972 if (lpTbb == NULL)
2973 return FALSE;
2974
2975 if (nIndex == -1) {
2976 /* EPP: this seems to be an undocumented call (from my IE4)
2977 * I assume in that case that:
2978 * - lpTbb->iString is a string pointer (not a string index in strings[] table
2979 * - index of insertion is at the end of existing buttons
2980 * I only see this happen with nIndex == -1, but it could have a special
2981 * meaning (like -nIndex (or ~nIndex) to get the real position of insertion).
2982 */
2983 int len = lstrlenA((char*)lpTbb->iString) + 2;
2984 LPSTR ptr = (LPSTR)COMCTL32_Alloc(len);
2985
2986 nIndex = infoPtr->nNumButtons;
2987 strcpy(ptr, (char*)lpTbb->iString);
2988 ptr[len - 1] = 0; /* ended by two '\0' */
2989 lpTbb->iString = TOOLBAR_AddStringA(hwnd, 0, (LPARAM)ptr);
2990 COMCTL32_Free(ptr);
2991
2992 } else if (nIndex < 0)
2993 return FALSE;
2994
2995
2996// TRACE (toolbar, "inserting button index=%d\n", nIndex);
2997 if (nIndex > infoPtr->nNumButtons) {
2998 nIndex = infoPtr->nNumButtons;
2999// TRACE (toolbar, "adjust index=%d\n", nIndex);
3000 }
3001
3002 oldButtons = infoPtr->buttons;
3003 infoPtr->nNumButtons++;
3004 infoPtr->buttons = (TBUTTON_INFO*)COMCTL32_Alloc (sizeof (TBUTTON_INFO) * infoPtr->nNumButtons);
3005 /* pre insert copy */
3006 if (nIndex > 0) {
3007 memcpy (&infoPtr->buttons[0], &oldButtons[0],
3008 nIndex * sizeof(TBUTTON_INFO));
3009 }
3010
3011 /* insert new button */
3012 infoPtr->buttons[nIndex].iBitmap = lpTbb->iBitmap;
3013 infoPtr->buttons[nIndex].idCommand = lpTbb->idCommand;
3014 infoPtr->buttons[nIndex].fsState = lpTbb->fsState;
3015 infoPtr->buttons[nIndex].fsStyle = lpTbb->fsStyle;
3016 infoPtr->buttons[nIndex].dwData = lpTbb->dwData;
3017 infoPtr->buttons[nIndex].iString = lpTbb->iString;
3018
3019 if ((infoPtr->hwndToolTip) && !(lpTbb->fsStyle & TBSTYLE_SEP)) {
3020 TTTOOLINFOA ti;
3021
3022 ZeroMemory (&ti, sizeof(TTTOOLINFOA));
3023 ti.cbSize = sizeof (TTTOOLINFOA);
3024 ti.hwnd = hwnd;
3025 ti.uId = lpTbb->idCommand;
3026 ti.hinst = 0;
3027 ti.lpszText = LPSTR_TEXTCALLBACKA;
3028
3029 SendMessageA (infoPtr->hwndToolTip, TTM_ADDTOOLA,
3030 0, (LPARAM)&ti);
3031 }
3032
3033 /* post insert copy */
3034 if (nIndex < infoPtr->nNumButtons - 1) {
3035 memcpy (&infoPtr->buttons[nIndex+1], &oldButtons[nIndex],
3036 (infoPtr->nNumButtons - nIndex - 1) * sizeof(TBUTTON_INFO));
3037 }
3038
3039 COMCTL32_Free (oldButtons);
3040
3041 TOOLBAR_CalcToolbar (hwnd);
3042
3043 InvalidateRect (hwnd, NULL, FALSE);
3044
3045 return TRUE;
3046}
3047
3048static LRESULT TOOLBAR_InsertButtonW (HWND hwnd, WPARAM wParam, LPARAM lParam)
3049{
3050 //CB: just call InsertButtonA, no Unicode used?!?
3051
3052 return TOOLBAR_InsertButtonA(hwnd,wParam,lParam);
3053}
3054
3055/* << TOOLBAR_InsertMarkHitTest >> */
3056
3057
3058static LRESULT
3059TOOLBAR_IsButtonChecked (HWND hwnd, WPARAM wParam, LPARAM lParam)
3060{
3061 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3062 INT nIndex;
3063
3064 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3065 if (nIndex == -1)
3066 return FALSE;
3067
3068 return (infoPtr->buttons[nIndex].fsState & TBSTATE_CHECKED);
3069}
3070
3071
3072static LRESULT
3073TOOLBAR_IsButtonEnabled (HWND hwnd, WPARAM wParam, LPARAM lParam)
3074{
3075 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3076 INT nIndex;
3077
3078 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3079 if (nIndex == -1)
3080 return FALSE;
3081
3082 return (infoPtr->buttons[nIndex].fsState & TBSTATE_ENABLED);
3083}
3084
3085
3086static LRESULT
3087TOOLBAR_IsButtonHidden (HWND hwnd, WPARAM wParam, LPARAM lParam)
3088{
3089 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3090 INT nIndex;
3091
3092 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3093 if (nIndex == -1)
3094 return FALSE;
3095
3096 return (infoPtr->buttons[nIndex].fsState & TBSTATE_HIDDEN);
3097}
3098
3099
3100static LRESULT
3101TOOLBAR_IsButtonHighlighted (HWND hwnd, WPARAM wParam, LPARAM lParam)
3102{
3103 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3104 INT nIndex;
3105
3106 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3107 if (nIndex == -1)
3108 return FALSE;
3109
3110 return (infoPtr->buttons[nIndex].fsState & TBSTATE_MARKED);
3111}
3112
3113
3114static LRESULT
3115TOOLBAR_IsButtonIndeterminate (HWND hwnd, WPARAM wParam, LPARAM lParam)
3116{
3117 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3118 INT nIndex;
3119
3120 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3121 if (nIndex == -1)
3122 return FALSE;
3123
3124 return (infoPtr->buttons[nIndex].fsState & TBSTATE_INDETERMINATE);
3125}
3126
3127
3128static LRESULT
3129TOOLBAR_IsButtonPressed (HWND hwnd, WPARAM wParam, LPARAM lParam)
3130{
3131 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3132 INT nIndex;
3133
3134 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3135 if (nIndex == -1)
3136 return FALSE;
3137
3138 return (infoPtr->buttons[nIndex].fsState & TBSTATE_PRESSED);
3139}
3140
3141
3142/* << TOOLBAR_LoadImages >> */
3143/* << TOOLBAR_MapAccelerator >> */
3144/* << TOOLBAR_MarkButton >> */
3145/* << TOOLBAR_MoveButton >> */
3146
3147
3148static LRESULT
3149TOOLBAR_PressButton (HWND hwnd, WPARAM wParam, LPARAM lParam)
3150{
3151 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3152 TBUTTON_INFO *btnPtr;
3153 HDC hdc;
3154 INT nIndex;
3155
3156 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3157 if (nIndex == -1)
3158 return FALSE;
3159
3160 btnPtr = &infoPtr->buttons[nIndex];
3161 if (LOWORD(lParam) == FALSE)
3162 btnPtr->fsState &= ~TBSTATE_PRESSED;
3163 else
3164 btnPtr->fsState |= TBSTATE_PRESSED;
3165
3166 hdc = GetDC (hwnd);
3167 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
3168 ReleaseDC (hwnd, hdc);
3169
3170 return TRUE;
3171}
3172
3173
3174/* << TOOLBAR_ReplaceBitmap >> */
3175
3176
3177static LRESULT
3178TOOLBAR_SaveRestoreA (HWND hwnd, WPARAM wParam, LPARAM lParam)
3179{
3180#if 0
3181 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3182 LPTBSAVEPARAMSA lpSave = (LPTBSAVEPARAMSA)lParam;
3183
3184 if (lpSave == NULL) return 0;
3185
3186 if ((BOOL)wParam) {
3187 /* save toolbar information */
3188// FIXME (toolbar, "save to \"%s\" \"%s\"\n",
3189// lpSave->pszSubKey, lpSave->pszValueName);
3190
3191
3192 }
3193 else {
3194 /* restore toolbar information */
3195
3196// FIXME (toolbar, "restore from \"%s\" \"%s\"\n",
3197// lpSave->pszSubKey, lpSave->pszValueName);
3198
3199
3200 }
3201#endif
3202
3203 return 0;
3204}
3205
3206static LRESULT TOOLBAR_SaveRestoreW(HWND hwnd,WPARAM wParam,LPARAM lParam)
3207{
3208#if 0
3209 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3210 LPTBSAVEPARAMSW lpSave = (LPTBSAVEPARAMSW)lParam;
3211
3212 if (lpSave == NULL) return 0;
3213
3214 if ((BOOL)wParam) {
3215 /* save toolbar information */
3216// FIXME (toolbar, "save to \"%s\" \"%s\"\n",
3217// lpSave->pszSubKey, lpSave->pszValueName);
3218
3219
3220 }
3221 else {
3222 /* restore toolbar information */
3223
3224// FIXME (toolbar, "restore from \"%s\" \"%s\"\n",
3225// lpSave->pszSubKey, lpSave->pszValueName);
3226
3227
3228 }
3229#endif
3230
3231 return 0;
3232}
3233
3234/* << TOOLBAR_SaveRestore32W >> */
3235
3236static LRESULT
3237TOOLBAR_SetAnchorHighlight (HWND hwnd, WPARAM wParam)
3238{
3239 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3240 BOOL bOldAnchor = infoPtr->bAnchor;
3241
3242 infoPtr->bAnchor = (BOOL)wParam;
3243
3244 return (LRESULT)bOldAnchor;
3245}
3246
3247
3248static LRESULT
3249TOOLBAR_SetBitmapSize (HWND hwnd, WPARAM wParam, LPARAM lParam)
3250{
3251 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3252
3253 if (((INT)LOWORD(lParam) <= 0) || ((INT)HIWORD(lParam) <= 0)) return FALSE;
3254
3255 /* Bitmap size can only be set before adding any button to the toolbar
3256 according to the documentation. */
3257 if( infoPtr->nNumButtons != 0 )
3258 return FALSE;
3259
3260 infoPtr->nBitmapWidth = (INT)LOWORD(lParam);
3261 infoPtr->nBitmapHeight = (INT)HIWORD(lParam);
3262
3263 return TRUE;
3264}
3265
3266
3267static LRESULT
3268TOOLBAR_SetButtonInfoA (HWND hwnd, WPARAM wParam, LPARAM lParam)
3269{
3270 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3271 LPTBBUTTONINFOA lptbbi = (LPTBBUTTONINFOA)lParam;
3272 TBUTTON_INFO *btnPtr;
3273 INT nIndex;
3274
3275 if (lptbbi == NULL)
3276 return FALSE;
3277 if (lptbbi->cbSize < sizeof(TBBUTTONINFOA))
3278 return FALSE;
3279
3280 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3281 if (nIndex == -1)
3282 return FALSE;
3283
3284 btnPtr = &infoPtr->buttons[nIndex];
3285 if (lptbbi->dwMask & TBIF_COMMAND)
3286 btnPtr->idCommand = lptbbi->idCommand;
3287 if (lptbbi->dwMask & TBIF_IMAGE)
3288 btnPtr->iBitmap = lptbbi->iImage;
3289 if (lptbbi->dwMask & TBIF_LPARAM)
3290 btnPtr->dwData = lptbbi->lParam;
3291/* if (lptbbi->dwMask & TBIF_SIZE) */
3292/* btnPtr->cx = lptbbi->cx; */
3293 if (lptbbi->dwMask & TBIF_STATE)
3294 btnPtr->fsState = lptbbi->fsState;
3295 if (lptbbi->dwMask & TBIF_STYLE)
3296 btnPtr->fsStyle = lptbbi->fsStyle;
3297
3298 if (lptbbi->dwMask & TBIF_TEXT) {
3299 if ((btnPtr->iString >= 0) ||
3300 (btnPtr->iString < infoPtr->nNumStrings)) {
3301#if 0
3302 CHAR **lpString = &infoPtr->strings[btnPtr->iString]; //wrong, it's Unicode!!!
3303 INT len = lstrlenA (lptbbi->pszText);
3304 *lpString = COMCTL32_ReAlloc (lpString, sizeof(char)*(len+1));
3305#endif
3306
3307 /* this is the ultimate sollution */
3308/* Str_SetPtrA (&infoPtr->strings[btnPtr->iString], lptbbi->pszText); */
3309 }
3310 }
3311
3312 return TRUE;
3313}
3314
3315static LRESULT TOOLBAR_SetButtonInfoW (HWND hwnd, WPARAM wParam, LPARAM lParam)
3316{
3317 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3318 LPTBBUTTONINFOW lptbbi = (LPTBBUTTONINFOW)lParam;
3319 TBUTTON_INFO *btnPtr;
3320 INT nIndex;
3321
3322 if (lptbbi == NULL)
3323 return FALSE;
3324 if (lptbbi->cbSize < sizeof(TBBUTTONINFOW))
3325 return FALSE;
3326
3327 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3328 if (nIndex == -1)
3329 return FALSE;
3330
3331 btnPtr = &infoPtr->buttons[nIndex];
3332 if (lptbbi->dwMask & TBIF_COMMAND)
3333 btnPtr->idCommand = lptbbi->idCommand;
3334 if (lptbbi->dwMask & TBIF_IMAGE)
3335 btnPtr->iBitmap = lptbbi->iImage;
3336 if (lptbbi->dwMask & TBIF_LPARAM)
3337 btnPtr->dwData = lptbbi->lParam;
3338/* if (lptbbi->dwMask & TBIF_SIZE) */
3339/* btnPtr->cx = lptbbi->cx; */
3340 if (lptbbi->dwMask & TBIF_STATE)
3341 btnPtr->fsState = lptbbi->fsState;
3342 if (lptbbi->dwMask & TBIF_STYLE)
3343 btnPtr->fsStyle = lptbbi->fsStyle;
3344
3345 if (lptbbi->dwMask & TBIF_TEXT) {
3346 if ((btnPtr->iString >= 0) ||
3347 (btnPtr->iString < infoPtr->nNumStrings)) {
3348#if 0
3349 WCHAR **lpString = &infoPtr->strings[btnPtr->iString];
3350 INT len = lstrlenW (lptbbi->pszText);
3351 *lpString = COMCTL32_ReAlloc (lpString, sizeof(wchar)*(len+1));
3352#endif
3353
3354 /* this is the ultimate sollution */
3355/* Str_SetPtrW (&infoPtr->strings[btnPtr->iString], lptbbi->pszText); */
3356 }
3357 }
3358
3359 return TRUE;
3360}
3361
3362static LRESULT
3363TOOLBAR_SetButtonSize (HWND hwnd, WPARAM wParam, LPARAM lParam)
3364{
3365 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3366
3367 if (((INT)LOWORD(lParam) <= 0) || ((INT)HIWORD(lParam) <= 0)) return FALSE;
3368
3369 /* Button size can only be set before adding any button to the toolbar
3370 according to the documentation. */
3371 if( infoPtr->nNumButtons != 0 )
3372 return FALSE;
3373
3374 infoPtr->nButtonWidth = (INT)LOWORD(lParam);
3375 infoPtr->nButtonHeight = (INT)HIWORD(lParam);
3376
3377 return TRUE;
3378}
3379
3380
3381static LRESULT
3382TOOLBAR_SetButtonWidth (HWND hwnd, WPARAM wParam, LPARAM lParam)
3383{
3384 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3385
3386 if (infoPtr == NULL)
3387 return FALSE;
3388
3389 infoPtr->cxMin = (INT)LOWORD(lParam);
3390 infoPtr->cxMax = (INT)HIWORD(lParam);
3391
3392 return TRUE;
3393}
3394
3395
3396static LRESULT
3397TOOLBAR_SetCmdId (HWND hwnd, WPARAM wParam, LPARAM lParam)
3398{
3399 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3400 INT nIndex = (INT)wParam;
3401
3402 if ((nIndex < 0) || (nIndex >= infoPtr->nNumButtons))
3403 return FALSE;
3404
3405 infoPtr->buttons[nIndex].idCommand = (INT)lParam;
3406
3407 if (infoPtr->hwndToolTip) {
3408
3409// FIXME (toolbar, "change tool tip!\n");
3410
3411 }
3412
3413 return TRUE;
3414}
3415
3416
3417/* << TOOLBAR_SetColorScheme >> */
3418
3419
3420static LRESULT
3421TOOLBAR_SetDisabledImageList (HWND hwnd, WPARAM wParam, LPARAM lParam)
3422{
3423 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3424 HIMAGELIST himlTemp;
3425
3426 himlTemp = infoPtr->himlDis;
3427 infoPtr->himlDis = (HIMAGELIST)lParam;
3428
3429 /* FIXME: redraw ? */
3430
3431 return (LRESULT)himlTemp;
3432}
3433
3434
3435static LRESULT
3436TOOLBAR_SetDrawTextFlags (HWND hwnd, WPARAM wParam, LPARAM lParam)
3437{
3438 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3439 DWORD dwTemp;
3440
3441 dwTemp = infoPtr->dwDTFlags;
3442 infoPtr->dwDTFlags =
3443 (infoPtr->dwDTFlags & (DWORD)wParam) | (DWORD)lParam;
3444
3445 return (LRESULT)dwTemp;
3446}
3447
3448
3449static LRESULT
3450TOOLBAR_SetExtendedStyle (HWND hwnd, WPARAM wParam, LPARAM lParam)
3451{
3452 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3453 DWORD dwTemp;
3454
3455 dwTemp = infoPtr->dwExStyle;
3456 infoPtr->dwExStyle = (DWORD)lParam;
3457
3458 return (LRESULT)dwTemp;
3459}
3460
3461
3462static LRESULT
3463TOOLBAR_SetHotImageList (HWND hwnd, WPARAM wParam, LPARAM lParam)
3464{
3465 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr(hwnd);
3466 HIMAGELIST himlTemp;
3467
3468 himlTemp = infoPtr->himlHot;
3469 infoPtr->himlHot = (HIMAGELIST)lParam;
3470
3471 /* FIXME: redraw ? */
3472
3473 return (LRESULT)himlTemp;
3474}
3475
3476
3477static LRESULT
3478TOOLBAR_SetHotItem (HWND hwnd, WPARAM wParam)
3479{
3480 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr(hwnd);
3481 INT nOldHotItem = infoPtr->nHotItem;
3482
3483 if (GetWindowLongA (hwnd, GWL_STYLE) & TBSTYLE_FLAT)
3484 {
3485 infoPtr->nHotItem = (INT)wParam;
3486
3487 /* FIXME: What else must be done ??? */
3488
3489 }
3490
3491 if (nOldHotItem < 0)
3492 return -1;
3493
3494 return (LRESULT)nOldHotItem;
3495}
3496
3497
3498static LRESULT
3499TOOLBAR_SetImageList (HWND hwnd, WPARAM wParam, LPARAM lParam)
3500{
3501 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3502 HIMAGELIST himlTemp;
3503
3504 himlTemp = infoPtr->himlDef;
3505 infoPtr->himlDef = (HIMAGELIST)lParam;
3506
3507 /* FIXME: redraw ? */
3508
3509 return (LRESULT)himlTemp;
3510}
3511
3512
3513static LRESULT
3514TOOLBAR_SetIndent (HWND hwnd, WPARAM wParam, LPARAM lParam)
3515{
3516 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3517
3518 infoPtr->nIndent = (INT)wParam;
3519
3520 TOOLBAR_CalcToolbar (hwnd);
3521
3522 InvalidateRect(hwnd, NULL, FALSE);
3523
3524 return TRUE;
3525}
3526
3527
3528/* << TOOLBAR_SetInsertMark >> */
3529
3530
3531static LRESULT
3532TOOLBAR_SetInsertMarkColor (HWND hwnd, WPARAM wParam, LPARAM lParam)
3533{
3534 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3535
3536 infoPtr->clrInsertMark = (COLORREF)lParam;
3537
3538 /* FIXME : redraw ??*/
3539
3540 return 0;
3541}
3542
3543
3544static LRESULT
3545TOOLBAR_SetMaxTextRows (HWND hwnd, WPARAM wParam, LPARAM lParam)
3546{
3547 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3548
3549 if (infoPtr == NULL)
3550 return FALSE;
3551
3552 infoPtr->nMaxTextRows = (INT)wParam;
3553
3554 return TRUE;
3555}
3556
3557
3558/* << TOOLBAR_SetPadding >> */
3559
3560
3561static LRESULT
3562TOOLBAR_SetParent (HWND hwnd, WPARAM wParam, LPARAM lParam)
3563{
3564 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3565 HWND hwndOldNotify;
3566
3567 if (infoPtr == NULL)
3568 return 0;
3569 hwndOldNotify = infoPtr->hwndNotify;
3570 infoPtr->hwndNotify = (HWND)wParam;
3571
3572 return hwndOldNotify;
3573}
3574
3575
3576static LRESULT
3577TOOLBAR_SetRows (HWND hwnd, WPARAM wParam, LPARAM lParam)
3578{
3579 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3580 LPRECT lprc = (LPRECT)lParam;
3581
3582 if (LOWORD(wParam) > 1) {
3583
3584// FIXME (toolbar, "multiple rows not supported!\n");
3585
3586 }
3587
3588 /* recalculate toolbar */
3589 TOOLBAR_CalcToolbar (hwnd);
3590
3591 /* return bounding rectangle */
3592 if (lprc) {
3593 lprc->left = infoPtr->rcBound.left;
3594 lprc->right = infoPtr->rcBound.right;
3595 lprc->top = infoPtr->rcBound.top;
3596 lprc->bottom = infoPtr->rcBound.bottom;
3597 }
3598
3599 /* repaint toolbar */
3600 InvalidateRect(hwnd, NULL, FALSE);
3601
3602 return 0;
3603}
3604
3605
3606static LRESULT
3607TOOLBAR_SetState (HWND hwnd, WPARAM wParam, LPARAM lParam)
3608{
3609 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3610 TBUTTON_INFO *btnPtr;
3611 HDC hdc;
3612 INT nIndex;
3613
3614 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3615 if (nIndex == -1)
3616 return FALSE;
3617
3618 btnPtr = &infoPtr->buttons[nIndex];
3619 btnPtr->fsState = LOWORD(lParam);
3620
3621 hdc = GetDC (hwnd);
3622 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
3623 ReleaseDC (hwnd, hdc);
3624
3625 return TRUE;
3626}
3627
3628
3629static LRESULT
3630TOOLBAR_SetStyle (HWND hwnd, WPARAM wParam, LPARAM lParam)
3631{
3632 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3633 TBUTTON_INFO *btnPtr;
3634 HDC hdc;
3635 INT nIndex;
3636
3637 nIndex = TOOLBAR_GetButtonIndex (infoPtr, (INT)wParam);
3638 if (nIndex == -1)
3639 return FALSE;
3640
3641 btnPtr = &infoPtr->buttons[nIndex];
3642 btnPtr->fsStyle = LOWORD(lParam);
3643
3644 hdc = GetDC (hwnd);
3645 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
3646 ReleaseDC (hwnd, hdc);
3647
3648 if (infoPtr->hwndToolTip) {
3649
3650// FIXME (toolbar, "change tool tip!\n");
3651
3652 }
3653
3654 return TRUE;
3655}
3656
3657
3658static LRESULT
3659TOOLBAR_SetToolTips (HWND hwnd, WPARAM wParam, LPARAM lParam)
3660{
3661 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3662
3663 if (infoPtr == NULL)
3664 return 0;
3665 infoPtr->hwndToolTip = (HWND)wParam;
3666 return 0;
3667}
3668
3669
3670static LRESULT
3671TOOLBAR_SetUnicodeFormat (HWND hwnd, WPARAM wParam, LPARAM lParam)
3672{
3673 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3674 BOOL bTemp;
3675
3676// TRACE (toolbar, "%s hwnd=0x%04x stub!\n",
3677// ((BOOL)wParam) ? "TRUE" : "FALSE", hwnd);
3678
3679 bTemp = infoPtr->bUnicode;
3680 infoPtr->bUnicode = (BOOL)wParam;
3681
3682 return bTemp;
3683}
3684
3685static LRESULT
3686TOOLBAR_SetVersion (HWND hwnd, INT iVersion)
3687{
3688 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3689 INT iOldVersion = infoPtr->iVersion;
3690
3691 infoPtr->iVersion = iVersion;
3692
3693 return iOldVersion;
3694}
3695
3696static LRESULT
3697TOOLBAR_Create (HWND hwnd, WPARAM wParam, LPARAM lParam)
3698{
3699 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3700 DWORD dwStyle = GetWindowLongA (hwnd, GWL_STYLE);
3701 LOGFONTA logFont;
3702
3703 /* initialize info structure */
3704 infoPtr->nButtonHeight = 22;
3705 infoPtr->nButtonWidth = 24;
3706 infoPtr->nBitmapHeight = 15;
3707 infoPtr->nBitmapWidth = 16;
3708
3709 infoPtr->nHeight = infoPtr->nButtonHeight + TOP_BORDER + BOTTOM_BORDER;
3710 infoPtr->nRows = 1;
3711 infoPtr->nMaxTextRows = 1;
3712 infoPtr->cxMin = -1;
3713 infoPtr->cxMax = -1;
3714
3715 infoPtr->bCaptured = FALSE;
3716 infoPtr->bUnicode = IsWindowUnicode(hwnd);
3717 infoPtr->nButtonDown = -1;
3718 infoPtr->nOldHit = -1;
3719 infoPtr->nHotItem = -2; /* It has to be initially different from nOldHit */
3720 infoPtr->hwndNotify = GetParent (hwnd);
3721 infoPtr->bTransparent = (dwStyle & TBSTYLE_FLAT);
3722 infoPtr->dwDTFlags = (dwStyle & TBSTYLE_LIST) ? DT_LEFT | DT_VCENTER | DT_SINGLELINE : DT_CENTER;
3723 infoPtr->bAnchor = FALSE; /* no anchor highlighting */
3724 infoPtr->iVersion = 0;
3725
3726 infoPtr->hwndToolbar = hwnd;
3727 infoPtr->oldButtons = NULL;
3728 infoPtr->nNumOldButtons = 0;
3729
3730 SystemParametersInfoA (SPI_GETICONTITLELOGFONT, 0, &logFont, 0);
3731 infoPtr->hFont = CreateFontIndirectA (&logFont);
3732
3733 if (dwStyle & TBSTYLE_TOOLTIPS)
3734 {
3735 /* Create tooltip control */
3736 infoPtr->hwndToolTip =
3737 CreateWindowExA (WS_EX_TOOLWINDOW,TOOLTIPS_CLASSA,NULL,WS_POPUP,
3738 CW_USEDEFAULT,CW_USEDEFAULT,
3739 CW_USEDEFAULT,CW_USEDEFAULT,
3740 hwnd,0,0,0);
3741
3742 /* Send NM_TOOLTIPSCREATED notification */
3743 if (infoPtr->hwndToolTip)
3744 {
3745 NMTOOLTIPSCREATED nmttc;
3746
3747 nmttc.hdr.hwndFrom = hwnd;
3748 nmttc.hdr.idFrom = GetWindowLongA(hwnd,GWL_ID);
3749 nmttc.hdr.code = NM_TOOLTIPSCREATED;
3750 nmttc.hwndToolTips = infoPtr->hwndToolTip;
3751
3752 SendMessageA(infoPtr->hwndNotify,WM_NOTIFY,(WPARAM)nmttc.hdr.idFrom,(LPARAM)&nmttc);
3753 }
3754 }
3755
3756 return 0;
3757}
3758
3759
3760static LRESULT
3761TOOLBAR_Destroy (HWND hwnd, WPARAM wParam, LPARAM lParam)
3762{
3763 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3764
3765 /* delete tooltip control */
3766 if (infoPtr->hwndToolTip)
3767 DestroyWindow (infoPtr->hwndToolTip);
3768
3769 /* delete button data */
3770 if (infoPtr->buttons)
3771 {
3772 INT x;
3773
3774 for (x = 0;x < infoPtr->nNumButtons;x++) COMCTL32_Free(infoPtr->buttons[x].pszName);
3775 COMCTL32_Free(infoPtr->buttons);
3776 }
3777
3778 /* delete strings */
3779 if (infoPtr->strings) {
3780 INT i;
3781 for (i = 0; i < infoPtr->nNumStrings; i++)
3782 if (infoPtr->strings[i])
3783 COMCTL32_Free (infoPtr->strings[i]);
3784
3785 COMCTL32_Free (infoPtr->strings);
3786 }
3787
3788 /* destroy internal image list */
3789 if (infoPtr->himlInt)
3790 ImageList_Destroy (infoPtr->himlInt);
3791
3792 /* delete default font */
3793 if (infoPtr->hFont)
3794 DeleteObject (infoPtr->hFont);
3795
3796 /* free toolbar info data */
3797 COMCTL32_Free (infoPtr);
3798 SetWindowLongA(hwnd, 0, 0);
3799
3800 return 0;
3801}
3802
3803
3804static LRESULT
3805TOOLBAR_EraseBackground (HWND hwnd, WPARAM wParam, LPARAM lParam)
3806{
3807 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3808
3809 //SvL: Check ptr
3810 if (infoPtr && infoPtr->bTransparent)
3811 return SendMessageA (GetParent (hwnd), WM_ERASEBKGND, wParam, lParam);
3812
3813 return DefWindowProcA (hwnd, WM_ERASEBKGND, wParam, lParam);
3814}
3815
3816static LRESULT
3817TOOLBAR_GetFont (HWND hwnd, WPARAM wParam, LPARAM lParam)
3818{
3819 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3820
3821 return infoPtr->hFont;
3822}
3823
3824static LRESULT
3825TOOLBAR_LButtonDblClk (HWND hwnd, WPARAM wParam, LPARAM lParam)
3826{
3827 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3828 TBUTTON_INFO *btnPtr;
3829 POINT pt;
3830 INT nHit;
3831 HDC hdc;
3832
3833 pt.x = (INT)LOWORD(lParam);
3834 pt.y = (INT)HIWORD(lParam);
3835 nHit = TOOLBAR_InternalHitTest (hwnd, &pt);
3836
3837 if (nHit >= 0) {
3838 btnPtr = &infoPtr->buttons[nHit];
3839 if (!(btnPtr->fsState & TBSTATE_ENABLED))
3840 return 0;
3841 SetCapture (hwnd);
3842 infoPtr->bCaptured = TRUE;
3843 infoPtr->nButtonDown = nHit;
3844
3845 btnPtr->fsState |= TBSTATE_PRESSED;
3846
3847 hdc = GetDC (hwnd);
3848 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
3849 ReleaseDC (hwnd, hdc);
3850 }
3851 else if (GetWindowLongA (hwnd, GWL_STYLE) & CCS_ADJUSTABLE)
3852 TOOLBAR_Customize (hwnd);
3853
3854 return 0;
3855}
3856
3857
3858static LRESULT
3859TOOLBAR_LButtonDown (HWND hwnd, WPARAM wParam, LPARAM lParam)
3860{
3861 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3862 TBUTTON_INFO *btnPtr;
3863 POINT pt;
3864 INT nHit;
3865 HDC hdc;
3866
3867 if (infoPtr->hwndToolTip)
3868 TOOLBAR_RelayEvent (infoPtr->hwndToolTip, hwnd,
3869 WM_LBUTTONDOWN, wParam, lParam);
3870
3871 pt.x = (INT)LOWORD(lParam);
3872 pt.y = (INT)HIWORD(lParam);
3873 nHit = TOOLBAR_InternalHitTest (hwnd, &pt);
3874
3875 if (nHit >= 0) {
3876 btnPtr = &infoPtr->buttons[nHit];
3877 if (!(btnPtr->fsState & TBSTATE_ENABLED))
3878 return 0;
3879
3880 if (btnPtr->fsStyle & TBSTYLE_DROPDOWN)
3881 {
3882 NMTOOLBARA nmtb;
3883
3884 nmtb.hdr.hwndFrom = hwnd;
3885 nmtb.hdr.idFrom = GetWindowLongA (hwnd, GWL_ID);
3886 nmtb.hdr.code = TBN_DROPDOWN;
3887 nmtb.iItem = btnPtr->idCommand;
3888
3889 SendMessageA (infoPtr->hwndNotify, WM_NOTIFY,
3890 (WPARAM)nmtb.hdr.idFrom, (LPARAM)&nmtb);
3891 }
3892
3893 SetCapture (hwnd);
3894 infoPtr->bCaptured = TRUE;
3895 infoPtr->nButtonDown = nHit;
3896 infoPtr->nOldHit = nHit;
3897
3898 btnPtr->fsState |= TBSTATE_PRESSED;
3899
3900 hdc = GetDC (hwnd);
3901 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
3902 ReleaseDC (hwnd, hdc);
3903 }
3904
3905 return 0;
3906}
3907
3908
3909static LRESULT
3910TOOLBAR_LButtonUp (HWND hwnd, WPARAM wParam, LPARAM lParam)
3911{
3912 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
3913 TBUTTON_INFO *btnPtr;
3914 POINT pt;
3915 INT nHit;
3916 INT nOldIndex = -1;
3917 HDC hdc;
3918 BOOL bSendMessage = TRUE;
3919
3920 if (infoPtr->hwndToolTip)
3921 TOOLBAR_RelayEvent (infoPtr->hwndToolTip, hwnd,
3922 WM_LBUTTONUP, wParam, lParam);
3923
3924 pt.x = (INT)LOWORD(lParam);
3925 pt.y = (INT)HIWORD(lParam);
3926 nHit = TOOLBAR_InternalHitTest (hwnd, &pt);
3927
3928 if ((infoPtr->bCaptured) && (infoPtr->nButtonDown >= 0)) {
3929 infoPtr->bCaptured = FALSE;
3930 ReleaseCapture ();
3931 btnPtr = &infoPtr->buttons[infoPtr->nButtonDown];
3932 btnPtr->fsState &= ~TBSTATE_PRESSED;
3933
3934 if (nHit == infoPtr->nButtonDown) {
3935 if (btnPtr->fsStyle & TBSTYLE_CHECK) {
3936 if (btnPtr->fsStyle & TBSTYLE_GROUP) {
3937 nOldIndex = TOOLBAR_GetCheckedGroupButtonIndex (infoPtr,
3938 infoPtr->nButtonDown);
3939 if (nOldIndex == infoPtr->nButtonDown)
3940 bSendMessage = FALSE;
3941 if ((nOldIndex != infoPtr->nButtonDown) &&
3942 (nOldIndex != -1))
3943 infoPtr->buttons[nOldIndex].fsState &= ~TBSTATE_CHECKED;
3944 btnPtr->fsState |= TBSTATE_CHECKED;
3945 }
3946 else {
3947 if (btnPtr->fsState & TBSTATE_CHECKED)
3948 btnPtr->fsState &= ~TBSTATE_CHECKED;
3949 else
3950 btnPtr->fsState |= TBSTATE_CHECKED;
3951 }
3952 }
3953 }
3954 else
3955 bSendMessage = FALSE;
3956
3957 hdc = GetDC (hwnd);
3958 if (nOldIndex != -1)
3959 TOOLBAR_DrawButton (hwnd, &infoPtr->buttons[nOldIndex], hdc);
3960 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
3961 ReleaseDC (hwnd, hdc);
3962
3963 if (bSendMessage) {
3964 SendMessageA (GetParent(hwnd), WM_COMMAND,
3965 MAKEWPARAM(btnPtr->idCommand, 0), (LPARAM)hwnd);
3966
3967 if ((GetWindowLongA(hwnd, GWL_STYLE) & TBSTYLE_DROPDOWN) ||
3968 (btnPtr->fsStyle & 0x08/* BTNS_DROPDOWN */)) {
3969 NMTOOLBARW nmtb;
3970
3971 nmtb.hdr.hwndFrom = hwnd;
3972 nmtb.hdr.idFrom = GetWindowLongA (hwnd, GWL_ID);
3973 nmtb.hdr.code = TBN_DROPDOWN;
3974 nmtb.iItem = nHit;
3975 /* nmtb.tbButton not used with TBN_DROPDOWN */
3976 if ((btnPtr->iString >= 0) && (btnPtr->iString < infoPtr->nNumStrings)) {
3977 nmtb.pszText = infoPtr->strings[btnPtr->iString];
3978 nmtb.cchText = lstrlenW(nmtb.pszText);
3979 } else {
3980 nmtb.pszText = NULL;
3981 nmtb.cchText = 0;
3982 }
3983 nmtb.rcButton = btnPtr->rect;
3984
3985 SendMessageW(infoPtr->hwndNotify, WM_NOTIFY,
3986 (WPARAM)nmtb.hdr.idFrom, (LPARAM)&nmtb);
3987 }
3988 }
3989
3990 infoPtr->nButtonDown = -1;
3991 infoPtr->nOldHit = -1;
3992 }
3993
3994 return 0;
3995}
3996
3997
3998static LRESULT
3999TOOLBAR_MouseMove (HWND hwnd, WPARAM wParam, LPARAM lParam)
4000{
4001 TBUTTON_INFO *btnPtr, *oldBtnPtr;
4002 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
4003 POINT pt;
4004 INT nHit;
4005 HDC hdc;
4006 DWORD dwStyle = GetWindowLongA(hwnd,GWL_STYLE);
4007
4008 if (infoPtr->hwndToolTip)
4009 TOOLBAR_RelayEvent (infoPtr->hwndToolTip,hwnd,
4010 WM_MOUSEMOVE,wParam,lParam);
4011
4012 pt.x = (INT)LOWORD(lParam);
4013 pt.y = (INT)HIWORD(lParam);
4014
4015 nHit = TOOLBAR_InternalHitTest(hwnd,&pt);
4016
4017 if (infoPtr->nOldHit != nHit)
4018 {
4019 /* Remove the effect of an old hot button */
4020 if(infoPtr->nOldHit == infoPtr->nHotItem)
4021 {
4022 oldBtnPtr = &infoPtr->buttons[infoPtr->nOldHit];
4023 if (oldBtnPtr->bHot) //CB: dynamic buttons
4024 {
4025 oldBtnPtr->bHot = FALSE;
4026
4027 if (dwStyle & TBSTYLE_FLAT) InvalidateRect(hwnd,&oldBtnPtr->rect,TRUE);
4028 }
4029 }
4030
4031 /* It's not a separator or in nowhere. It's a hot button. */
4032 if (nHit >= 0)
4033 {
4034 btnPtr = &infoPtr->buttons[nHit];
4035 if (!btnPtr->bHot)
4036 {
4037 btnPtr->bHot = TRUE;
4038
4039 if (dwStyle & TBSTYLE_FLAT)
4040 {
4041 hdc = GetDC (hwnd);
4042 TOOLBAR_DrawButton (hwnd, btnPtr, hdc);
4043 ReleaseDC (hwnd, hdc);
4044 }
4045
4046 infoPtr->nHotItem = nHit;
4047 }
4048 }
4049
4050 if (infoPtr->bCaptured)
4051 {
4052 btnPtr = &infoPtr->buttons[infoPtr->nButtonDown];
4053 if (infoPtr->nOldHit == infoPtr->nButtonDown)
4054 {
4055 btnPtr->fsState &= ~TBSTATE_PRESSED;
4056
4057 hdc = GetDC (hwnd);
4058 TOOLBAR_DrawButton(hwnd,btnPtr,hdc);
4059 ReleaseDC(hwnd,hdc);
4060 } else if (nHit == infoPtr->nButtonDown)
4061 {
4062 btnPtr->fsState |= TBSTATE_PRESSED;
4063
4064 hdc = GetDC(hwnd);
4065 TOOLBAR_DrawButton(hwnd,btnPtr,hdc);
4066 ReleaseDC(hwnd,hdc);
4067 }
4068 }
4069 infoPtr->nOldHit = nHit;
4070 }
4071 return 0;
4072}
4073
4074
4075static LRESULT
4076TOOLBAR_NCActivate (HWND hwnd, WPARAM wParam, LPARAM lParam)
4077{
4078/* if (wndPtr->dwStyle & CCS_NODIVIDER) */
4079 return DefWindowProcA (hwnd, WM_NCACTIVATE, wParam, lParam);
4080/* else */
4081/* return TOOLBAR_NCPaint (wndPtr, wParam, lParam); */
4082}
4083
4084
4085static LRESULT
4086TOOLBAR_NCCalcSize (HWND hwnd, WPARAM wParam, LPARAM lParam)
4087{
4088 if (!(GetWindowLongA (hwnd, GWL_STYLE) & CCS_NODIVIDER))
4089 ((LPRECT)lParam)->top += GetSystemMetrics(SM_CYEDGE);
4090
4091 return DefWindowProcA (hwnd, WM_NCCALCSIZE, wParam, lParam);
4092}
4093
4094
4095static LRESULT
4096TOOLBAR_NCCreate (HWND hwnd, WPARAM wParam, LPARAM lParam)
4097{
4098 TOOLBAR_INFO *infoPtr;
4099
4100 /* allocate memory for info structure */
4101 infoPtr = (TOOLBAR_INFO *)COMCTL32_Alloc (sizeof(TOOLBAR_INFO));
4102 SetWindowLongA (hwnd, 0, (DWORD)infoPtr);
4103
4104 /* paranoid!! */
4105 infoPtr->dwStructSize = sizeof(TBBUTTON);
4106
4107 /* fix instance handle, if the toolbar was created by CreateToolbarEx() */
4108 if (!GetWindowLongA (hwnd, GWL_HINSTANCE)) {
4109 HINSTANCE hInst = (HINSTANCE)GetWindowLongA (GetParent (hwnd), GWL_HINSTANCE);
4110 SetWindowLongA (hwnd, GWL_HINSTANCE, (DWORD)hInst);
4111 }
4112
4113 return DefWindowProcA (hwnd, WM_NCCREATE, wParam, lParam);
4114}
4115
4116
4117static LRESULT
4118TOOLBAR_NCPaint (HWND hwnd, WPARAM wParam, LPARAM lParam)
4119{
4120 DWORD dwStyle = GetWindowLongA (hwnd, GWL_STYLE);
4121 RECT rcWindow;
4122 HDC hdc;
4123
4124 if (dwStyle & WS_MINIMIZE)
4125 return 0; /* Nothing to do */
4126
4127 DefWindowProcA (hwnd, WM_NCPAINT, wParam, lParam);
4128
4129 if (!(hdc = GetDCEx (hwnd, 0, DCX_USESTYLE | DCX_WINDOW)))
4130 return 0;
4131
4132 if (!(dwStyle & CCS_NODIVIDER))
4133 {
4134 GetWindowRect (hwnd, &rcWindow);
4135 OffsetRect (&rcWindow, -rcWindow.left, -rcWindow.top);
4136 if( dwStyle & WS_BORDER )
4137 OffsetRect (&rcWindow, 1, 1);
4138 DrawEdge (hdc, &rcWindow, EDGE_ETCHED, BF_TOP);
4139 }
4140
4141 ReleaseDC( hwnd, hdc );
4142
4143 return 0;
4144}
4145
4146
4147static LRESULT
4148TOOLBAR_Notify (HWND hwnd, WPARAM wParam, LPARAM lParam)
4149{
4150 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
4151 LPNMHDR lpnmh = (LPNMHDR)lParam;
4152
4153// TRACE (toolbar, "passing WM_NOTIFY!\n");
4154
4155 if ((infoPtr->hwndToolTip) && (lpnmh->hwndFrom == infoPtr->hwndToolTip)) {
4156 SendMessageA (infoPtr->hwndNotify, WM_NOTIFY, wParam, lParam);
4157
4158#if 0
4159 if (lpnmh->code == TTN_GETDISPINFOA) {
4160 LPNMTTDISPINFOA lpdi = (LPNMTTDISPINFOA)lParam;
4161
4162// FIXME (toolbar, "retrieving ASCII string\n");
4163
4164 }
4165 else if (lpnmh->code == TTN_GETDISPINFOW) {
4166 LPNMTTDISPINFOW lpdi = (LPNMTTDISPINFOW)lParam;
4167
4168// FIXME (toolbar, "retrieving UNICODE string\n");
4169
4170 }
4171#endif
4172 }
4173
4174 return 0;
4175}
4176
4177
4178static LRESULT
4179TOOLBAR_Paint (HWND hwnd, WPARAM wParam)
4180{
4181 HDC hdc;
4182 PAINTSTRUCT ps;
4183
4184 TOOLBAR_CalcToolbar(hwnd);
4185 hdc = wParam == 0 ? BeginPaint(hwnd,&ps) : (HDC)wParam;
4186 TOOLBAR_Refresh(hwnd,hdc);
4187 if (!wParam) EndPaint (hwnd, &ps);
4188 return 0;
4189}
4190
4191
4192static LRESULT
4193TOOLBAR_Size (HWND hwnd, WPARAM wParam, LPARAM lParam)
4194{
4195 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
4196 DWORD dwStyle = GetWindowLongA (hwnd, GWL_STYLE);
4197 RECT parent_rect;
4198 HWND parent;
4199 INT x = 0,y = 0,cx,cy;
4200 INT flags;
4201 UINT uPosFlags = 0;
4202
4203 /* Resize deadlock check */
4204 if (infoPtr->bAutoSize) {
4205 infoPtr->bAutoSize = FALSE;
4206 return 0;
4207 }
4208
4209 flags = (INT) wParam;
4210
4211 /* FIXME for flags =
4212 * SIZE_MAXIMIZED, SIZE_MAXSHOW, SIZE_MINIMIZED
4213 */
4214
4215 //TRACE (toolbar, "sizing toolbar!\n");
4216
4217 if (flags == SIZE_RESTORED) {
4218 /* width and height don't apply */
4219 parent = GetParent (hwnd);
4220 GetClientRect(parent, &parent_rect);
4221 x = parent_rect.left;
4222 y = parent_rect.top;
4223
4224 if (dwStyle & CCS_NORESIZE) {
4225 uPosFlags |= (SWP_NOSIZE | SWP_NOMOVE);
4226 /* FIXME */
4227/* infoPtr->nWidth = parent_rect.right - parent_rect.left; */
4228 cy = infoPtr->nHeight;
4229 cx = infoPtr->nWidth;
4230 TOOLBAR_CalcToolbar (hwnd);
4231 infoPtr->nWidth = cx;
4232 infoPtr->nHeight = cy;
4233 }
4234 else {
4235 infoPtr->nWidth = parent_rect.right - parent_rect.left;
4236 TOOLBAR_CalcToolbar (hwnd);
4237 cy = infoPtr->nHeight;
4238 cx = infoPtr->nWidth;
4239 }
4240
4241 if (dwStyle & CCS_NOPARENTALIGN) {
4242 uPosFlags |= SWP_NOMOVE;
4243 cy = infoPtr->nHeight;
4244 cx = infoPtr->nWidth;
4245 }
4246
4247 if (!(dwStyle & CCS_NODIVIDER))
4248 cy += GetSystemMetrics(SM_CYEDGE);
4249
4250 if (dwStyle & WS_BORDER)
4251 {
4252 x = y = 1;
4253 cy += GetSystemMetrics(SM_CYEDGE);
4254 cx += GetSystemMetrics(SM_CYEDGE);
4255 }
4256
4257 SetWindowPos (hwnd, 0, parent_rect.left - x, parent_rect.top - y,
4258 cx, cy, uPosFlags | SWP_NOZORDER);
4259 }
4260 return 0;
4261}
4262
4263
4264static LRESULT
4265TOOLBAR_StyleChanged (HWND hwnd, INT nType, LPSTYLESTRUCT lpStyle)
4266{
4267 TOOLBAR_INFO *infoPtr = TOOLBAR_GetInfoPtr (hwnd);
4268
4269 if (nType == GWL_STYLE) {
4270 if (lpStyle->styleNew & TBSTYLE_LIST) {
4271 infoPtr->dwDTFlags = DT_LEFT | DT_VCENTER | DT_SINGLELINE;
4272 }
4273 else {
4274 infoPtr->dwDTFlags = DT_CENTER;
4275 }
4276 }
4277
4278 TOOLBAR_AutoSize (hwnd);
4279
4280 InvalidateRect(hwnd, NULL, FALSE);
4281
4282 return 0;
4283}
4284
4285
4286
4287static LRESULT WINAPI
4288ToolbarWindowProc (HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
4289{
4290 switch (uMsg)
4291 {
4292 case WM_DESTROY:
4293 return TOOLBAR_Destroy (hwnd, wParam, lParam);
4294
4295 case WM_NCCREATE:
4296 return TOOLBAR_NCCreate (hwnd, wParam, lParam);
4297 }
4298
4299 if (!TOOLBAR_GetInfoPtr (hwnd))
4300 {
4301 return DefWindowProcA (hwnd, uMsg, wParam, lParam);
4302 }
4303
4304 switch (uMsg)
4305 {
4306 case TB_ADDBITMAP:
4307 return TOOLBAR_AddBitmap (hwnd, wParam, lParam);
4308
4309 case TB_ADDBUTTONSA:
4310 return TOOLBAR_AddButtonsA (hwnd, wParam, lParam);
4311
4312 case TB_ADDBUTTONSW:
4313 return TOOLBAR_AddButtonsW(hwnd,wParam,lParam);
4314
4315 case TB_ADDSTRINGA:
4316 return TOOLBAR_AddStringA (hwnd, wParam, lParam);
4317
4318 case TB_ADDSTRINGW:
4319 return TOOLBAR_AddStringW (hwnd, wParam, lParam);
4320
4321 case TB_AUTOSIZE:
4322 return TOOLBAR_AutoSize (hwnd);
4323
4324 case TB_BUTTONCOUNT:
4325 return TOOLBAR_ButtonCount (hwnd, wParam, lParam);
4326
4327 case TB_BUTTONSTRUCTSIZE:
4328 return TOOLBAR_ButtonStructSize (hwnd, wParam, lParam);
4329
4330 case TB_CHANGEBITMAP:
4331 return TOOLBAR_ChangeBitmap (hwnd, wParam, lParam);
4332
4333 case TB_CHECKBUTTON:
4334 return TOOLBAR_CheckButton (hwnd, wParam, lParam);
4335
4336 case TB_COMMANDTOINDEX:
4337 return TOOLBAR_CommandToIndex (hwnd, wParam, lParam);
4338
4339 case TB_CUSTOMIZE:
4340 return TOOLBAR_Customize (hwnd);
4341
4342 case TB_DELETEBUTTON:
4343 return TOOLBAR_DeleteButton (hwnd, wParam, lParam);
4344
4345 case TB_ENABLEBUTTON:
4346 return TOOLBAR_EnableButton (hwnd, wParam, lParam);
4347
4348 case TB_GETANCHORHIGHLIGHT:
4349 return TOOLBAR_GetAnchorHighlight (hwnd);
4350
4351 case TB_GETBITMAP:
4352 return TOOLBAR_GetBitmap (hwnd, wParam, lParam);
4353
4354 case TB_GETBITMAPFLAGS:
4355 return TOOLBAR_GetBitmapFlags (hwnd, wParam, lParam);
4356
4357 case TB_GETBUTTON:
4358 return TOOLBAR_GetButton (hwnd, wParam, lParam);
4359
4360 case TB_GETBUTTONINFOA:
4361 return TOOLBAR_GetButtonInfoA (hwnd, wParam, lParam);
4362
4363 case TB_GETBUTTONINFOW: /* 4.71 */
4364 return TOOLBAR_GetButtonInfoW(hwnd,wParam,lParam);
4365
4366 case TB_GETBUTTONSIZE:
4367 return TOOLBAR_GetButtonSize (hwnd);
4368
4369 case TB_GETBUTTONTEXTA:
4370 return TOOLBAR_GetButtonTextA (hwnd, wParam, lParam);
4371
4372 case TB_GETBUTTONTEXTW:
4373 return TOOLBAR_GetButtonTextW(hwnd,wParam,lParam);
4374
4375/* case TB_GETCOLORSCHEME: */ /* 4.71 */
4376
4377 case TB_GETDISABLEDIMAGELIST:
4378 return TOOLBAR_GetDisabledImageList (hwnd, wParam, lParam);
4379
4380 case TB_GETEXTENDEDSTYLE:
4381 return TOOLBAR_GetExtendedStyle (hwnd);
4382
4383 case TB_GETHOTIMAGELIST:
4384 return TOOLBAR_GetHotImageList (hwnd, wParam, lParam);
4385
4386 case TB_GETHOTITEM:
4387 return TOOLBAR_GetHotItem (hwnd);
4388
4389 case TB_GETIMAGELIST:
4390 return TOOLBAR_GetImageList (hwnd, wParam, lParam);
4391
4392/* case TB_GETINSERTMARK: */ /* 4.71 */
4393/* case TB_GETINSERTMARKCOLOR: */ /* 4.71 */
4394
4395 case TB_GETITEMRECT:
4396 return TOOLBAR_GetItemRect (hwnd, wParam, lParam);
4397
4398 case TB_GETMAXSIZE:
4399 return TOOLBAR_GetMaxSize (hwnd, wParam, lParam);
4400
4401/* case TB_GETOBJECT: */ /* 4.71 */
4402/* case TB_GETPADDING: */ /* 4.71 */
4403
4404 case TB_GETRECT:
4405 return TOOLBAR_GetRect (hwnd, wParam, lParam);
4406
4407 case TB_GETROWS:
4408 return TOOLBAR_GetRows (hwnd, wParam, lParam);
4409
4410 case TB_GETSTATE:
4411 return TOOLBAR_GetState (hwnd, wParam, lParam);
4412
4413 case TB_GETSTYLE:
4414 return TOOLBAR_GetStyle (hwnd, wParam, lParam);
4415
4416 case TB_GETTEXTROWS:
4417 return TOOLBAR_GetTextRows (hwnd, wParam, lParam);
4418
4419 case TB_GETTOOLTIPS:
4420 return TOOLBAR_GetToolTips (hwnd, wParam, lParam);
4421
4422 case TB_GETUNICODEFORMAT:
4423 return TOOLBAR_GetUnicodeFormat (hwnd, wParam, lParam);
4424
4425 case CCM_GETVERSION:
4426 return TOOLBAR_GetVersion (hwnd);
4427
4428 case TB_HIDEBUTTON:
4429 return TOOLBAR_HideButton (hwnd, wParam, lParam);
4430
4431 case TB_HITTEST:
4432 return TOOLBAR_HitTest (hwnd, wParam, lParam);
4433
4434 case TB_INDETERMINATE:
4435 return TOOLBAR_Indeterminate (hwnd, wParam, lParam);
4436
4437 case TB_INSERTBUTTONA:
4438 return TOOLBAR_InsertButtonA (hwnd, wParam, lParam);
4439
4440 case TB_INSERTBUTTONW:
4441 return TOOLBAR_InsertButtonW(hwnd,wParam,lParam);
4442
4443/* case TB_INSERTMARKHITTEST: */ /* 4.71 */
4444
4445 case TB_ISBUTTONCHECKED:
4446 return TOOLBAR_IsButtonChecked (hwnd, wParam, lParam);
4447
4448 case TB_ISBUTTONENABLED:
4449 return TOOLBAR_IsButtonEnabled (hwnd, wParam, lParam);
4450
4451 case TB_ISBUTTONHIDDEN:
4452 return TOOLBAR_IsButtonHidden (hwnd, wParam, lParam);
4453
4454 case TB_ISBUTTONHIGHLIGHTED:
4455 return TOOLBAR_IsButtonHighlighted (hwnd, wParam, lParam);
4456
4457 case TB_ISBUTTONINDETERMINATE:
4458 return TOOLBAR_IsButtonIndeterminate (hwnd, wParam, lParam);
4459
4460 case TB_ISBUTTONPRESSED:
4461 return TOOLBAR_IsButtonPressed (hwnd, wParam, lParam);
4462
4463 case TB_LOADIMAGES: /* 4.70 */
4464// FIXME("missing standard imagelists\n");
4465 return 0;
4466/* case TB_MAPACCELERATORA: */ /* 4.71 */
4467/* case TB_MAPACCELERATORW: */ /* 4.71 */
4468/* case TB_MARKBUTTON: */ /* 4.71 */
4469/* case TB_MOVEBUTTON: */ /* 4.71 */
4470
4471 case TB_PRESSBUTTON:
4472 return TOOLBAR_PressButton (hwnd, wParam, lParam);
4473
4474/* case TB_REPLACEBITMAP: */
4475
4476 case TB_SAVERESTOREA:
4477 return TOOLBAR_SaveRestoreA (hwnd, wParam, lParam);
4478
4479 case TB_SAVERESTOREW:
4480 return TOOLBAR_SaveRestoreW(hwnd,wParam,lParam);
4481
4482 case TB_SETANCHORHIGHLIGHT:
4483 return TOOLBAR_SetAnchorHighlight (hwnd, wParam);
4484
4485 case TB_SETBITMAPSIZE:
4486 return TOOLBAR_SetBitmapSize (hwnd, wParam, lParam);
4487
4488 case TB_SETBUTTONINFOA:
4489 return TOOLBAR_SetButtonInfoA (hwnd, wParam, lParam);
4490
4491 case TB_SETBUTTONINFOW: /* 4.71 */
4492 return TOOLBAR_SetButtonInfoW(hwnd,wParam,lParam);
4493
4494 case TB_SETBUTTONSIZE:
4495 return TOOLBAR_SetButtonSize (hwnd, wParam, lParam);
4496
4497 case TB_SETBUTTONWIDTH:
4498 return TOOLBAR_SetButtonWidth (hwnd, wParam, lParam);
4499
4500 case TB_SETCMDID:
4501 return TOOLBAR_SetCmdId (hwnd, wParam, lParam);
4502
4503/* case TB_SETCOLORSCHEME: */ /* 4.71 */
4504
4505 case TB_SETDISABLEDIMAGELIST:
4506 return TOOLBAR_SetDisabledImageList (hwnd, wParam, lParam);
4507
4508 case TB_SETDRAWTEXTFLAGS:
4509 return TOOLBAR_SetDrawTextFlags (hwnd, wParam, lParam);
4510
4511 case TB_SETEXTENDEDSTYLE:
4512 return TOOLBAR_SetExtendedStyle (hwnd, wParam, lParam);
4513
4514 case TB_SETHOTIMAGELIST:
4515 return TOOLBAR_SetHotImageList (hwnd, wParam, lParam);
4516
4517 case TB_SETHOTITEM:
4518 return TOOLBAR_SetHotItem (hwnd, wParam);
4519
4520 case TB_SETIMAGELIST:
4521 return TOOLBAR_SetImageList (hwnd, wParam, lParam);
4522
4523 case TB_SETINDENT:
4524 return TOOLBAR_SetIndent (hwnd, wParam, lParam);
4525
4526/* case TB_SETINSERTMARK: */ /* 4.71 */
4527
4528 case TB_SETINSERTMARKCOLOR:
4529 return TOOLBAR_SetInsertMarkColor (hwnd, wParam, lParam);
4530
4531 case TB_SETMAXTEXTROWS:
4532 return TOOLBAR_SetMaxTextRows (hwnd, wParam, lParam);
4533
4534/* case TB_SETPADDING: */ /* 4.71 */
4535
4536 case TB_SETPARENT:
4537 return TOOLBAR_SetParent (hwnd, wParam, lParam);
4538
4539 case TB_SETROWS:
4540 return TOOLBAR_SetRows (hwnd, wParam, lParam);
4541
4542 case TB_SETSTATE:
4543 return TOOLBAR_SetState (hwnd, wParam, lParam);
4544
4545 case TB_SETSTYLE:
4546 return TOOLBAR_SetStyle (hwnd, wParam, lParam);
4547
4548 case TB_SETTOOLTIPS:
4549 return TOOLBAR_SetToolTips (hwnd, wParam, lParam);
4550
4551 case TB_SETUNICODEFORMAT:
4552 return TOOLBAR_SetUnicodeFormat (hwnd, wParam, lParam);
4553
4554 case CCM_SETVERSION:
4555 return TOOLBAR_SetVersion (hwnd, (INT)wParam);
4556
4557/* case WM_CHAR: */
4558
4559 case WM_CREATE:
4560 return TOOLBAR_Create (hwnd, wParam, lParam);
4561
4562 case WM_ERASEBKGND:
4563 return TOOLBAR_EraseBackground (hwnd, wParam, lParam);
4564
4565 case WM_GETFONT:
4566 return TOOLBAR_GetFont (hwnd, wParam, lParam);
4567
4568/* case WM_KEYDOWN: */
4569/* case WM_KILLFOCUS: */
4570
4571 case WM_LBUTTONDBLCLK:
4572 return TOOLBAR_LButtonDblClk (hwnd, wParam, lParam);
4573
4574 case WM_LBUTTONDOWN:
4575 return TOOLBAR_LButtonDown (hwnd, wParam, lParam);
4576
4577 case WM_LBUTTONUP:
4578 return TOOLBAR_LButtonUp (hwnd, wParam, lParam);
4579
4580 case WM_MOUSEMOVE:
4581 return TOOLBAR_MouseMove (hwnd, wParam, lParam);
4582
4583 case WM_NCACTIVATE:
4584 return TOOLBAR_NCActivate (hwnd, wParam, lParam);
4585
4586 case WM_NCCALCSIZE:
4587 return TOOLBAR_NCCalcSize (hwnd, wParam, lParam);
4588
4589 case WM_NCPAINT:
4590 return TOOLBAR_NCPaint (hwnd, wParam, lParam);
4591
4592 case WM_NOTIFY:
4593 return TOOLBAR_Notify (hwnd, wParam, lParam);
4594
4595/* case WM_NOTIFYFORMAT: */
4596
4597 case WM_PAINT:
4598 return TOOLBAR_Paint (hwnd, wParam);
4599
4600 case WM_SIZE:
4601 return TOOLBAR_Size (hwnd, wParam, lParam);
4602
4603 case WM_STYLECHANGED:
4604 return TOOLBAR_StyleChanged (hwnd, (INT)wParam, (LPSTYLESTRUCT)lParam);
4605
4606/* case WM_SYSCOLORCHANGE: */
4607
4608/* case WM_WININICHANGE: */
4609
4610 case WM_CHARTOITEM:
4611 case WM_COMMAND:
4612 case WM_DRAWITEM:
4613 case WM_MEASUREITEM:
4614 case WM_VKEYTOITEM:
4615 return SendMessageA (GetParent (hwnd), uMsg, wParam, lParam);
4616
4617 default:
4618// if (uMsg >= WM_USER)
4619// ERR (toolbar, "unknown msg %04x wp=%08x lp=%08lx\n",
4620// uMsg, wParam, lParam);
4621 return DefWindowProcA (hwnd, uMsg, wParam, lParam);
4622 }
4623 return 0;
4624}
4625
4626
4627VOID
4628TOOLBAR_Register (VOID)
4629{
4630 WNDCLASSA wndClass;
4631
4632 ZeroMemory (&wndClass, sizeof(WNDCLASSA));
4633 wndClass.style = CS_GLOBALCLASS | CS_DBLCLKS;
4634 wndClass.lpfnWndProc = (WNDPROC)ToolbarWindowProc;
4635 wndClass.cbClsExtra = 0;
4636 wndClass.cbWndExtra = sizeof(TOOLBAR_INFO *);
4637 wndClass.hCursor = LoadCursorA (0, IDC_ARROWA);
4638 wndClass.hbrBackground = (HBRUSH)(COLOR_3DFACE + 1);
4639 wndClass.lpszClassName = TOOLBARCLASSNAMEA;
4640
4641 RegisterClassA (&wndClass);
4642}
4643
4644
4645VOID
4646TOOLBAR_Unregister (VOID)
4647{
4648 UnregisterClassA (TOOLBARCLASSNAMEA, (HINSTANCE)NULL);
4649}
4650
Note: See TracBrowser for help on using the repository browser.