4 * Copyright 1998,1999 Eric Kohl
7 * - A little bug in TOOLBAR_DrawMasked()
8 * - Button wrapping (under construction).
12 * - Tooltip support (almost complete).
14 * - Fix TOOLBAR_SetButtonInfo32A.
15 * - Customize dialog (under construction).
18 * - Run tests using Waite Group Windows95 API Bible Volume 2.
19 * The second cdrom contains executables addstr.exe, btncount.exe,
20 * btnstate.exe, butstrsz.exe, chkbtn.exe, chngbmp.exe, customiz.exe,
21 * enablebtn.exe, getbmp.exe, getbtn.exe, getflags.exe, hidebtn.exe,
22 * indetbtn.exe, insbtn.exe, pressbtn.exe, setbtnsz.exe, setcmdid.exe,
23 * setparnt.exe, setrows.exe, toolwnd.exe.
24 * - Microsofts controlspy examples.
36 #include "debugtools.h"
38 DEFAULT_DEBUG_CHANNEL(toolbar
)
40 #define SEPARATOR_WIDTH 8
42 #define BOTTOM_BORDER 2
44 #define TOOLBAR_GetInfoPtr(hwnd) ((TOOLBAR_INFO *)GetWindowLongA(hwnd,0))
48 TOOLBAR_DrawFlatSeparator (LPRECT lpRect
, HDC hdc
)
50 INT x
= (lpRect
->left
+ lpRect
->right
) / 2 - 1;
51 INT yBottom
= lpRect
->bottom
- 3;
52 INT yTop
= lpRect
->top
+ 1;
54 SelectObject ( hdc
, GetSysColorPen (COLOR_3DSHADOW
));
55 MoveToEx (hdc
, x
, yBottom
, NULL
);
56 LineTo (hdc
, x
, yTop
);
58 SelectObject ( hdc
, GetSysColorPen (COLOR_3DHILIGHT
));
59 MoveToEx (hdc
, x
, yBottom
, NULL
);
60 LineTo (hdc
, x
, yTop
);
65 TOOLBAR_DrawString (TOOLBAR_INFO
*infoPtr
, TBUTTON_INFO
*btnPtr
,
68 RECT rcText
= btnPtr
->rect
;
74 if ((btnPtr
->iString
> -1) && (btnPtr
->iString
< infoPtr
->nNumStrings
)) {
75 InflateRect (&rcText
, -3, -3);
76 rcText
.top
+= infoPtr
->nBitmapHeight
;
77 if (nState
& (TBSTATE_PRESSED
| TBSTATE_CHECKED
))
78 OffsetRect (&rcText
, 1, 1);
80 hOldFont
= SelectObject (hdc
, infoPtr
->hFont
);
81 nOldBkMode
= SetBkMode (hdc
, TRANSPARENT
);
82 if (!(nState
& TBSTATE_ENABLED
)) {
83 clrOld
= SetTextColor (hdc
, GetSysColor (COLOR_3DHILIGHT
));
84 OffsetRect (&rcText
, 1, 1);
85 DrawTextW (hdc
, infoPtr
->strings
[btnPtr
->iString
], -1,
86 &rcText
, infoPtr
->dwDTFlags
);
87 SetTextColor (hdc
, GetSysColor (COLOR_3DSHADOW
));
88 OffsetRect (&rcText
, -1, -1);
89 DrawTextW (hdc
, infoPtr
->strings
[btnPtr
->iString
], -1,
90 &rcText
, infoPtr
->dwDTFlags
);
92 else if (nState
& TBSTATE_INDETERMINATE
) {
93 clrOld
= SetTextColor (hdc
, GetSysColor (COLOR_3DSHADOW
));
94 DrawTextW (hdc
, infoPtr
->strings
[btnPtr
->iString
], -1,
95 &rcText
, infoPtr
->dwDTFlags
);
98 clrOld
= SetTextColor (hdc
, GetSysColor (COLOR_BTNTEXT
));
99 DrawTextW (hdc
, infoPtr
->strings
[btnPtr
->iString
], -1,
100 &rcText
, infoPtr
->dwDTFlags
);
103 SetTextColor (hdc
, clrOld
);
104 SelectObject (hdc
, hOldFont
);
105 if (nOldBkMode
!= TRANSPARENT
)
106 SetBkMode (hdc
, nOldBkMode
);
112 TOOLBAR_DrawPattern (HDC hdc
, LPRECT lpRect
)
114 HBRUSH hbr
= SelectObject (hdc
, CACHE_GetPattern55AABrush ());
115 INT cx
= lpRect
->right
- lpRect
->left
;
116 INT cy
= lpRect
->bottom
- lpRect
->top
;
117 PatBlt (hdc
, lpRect
->left
, lpRect
->top
, cx
, cy
, 0x00FA0089);
118 SelectObject (hdc
, hbr
);
123 TOOLBAR_DrawMasked (TOOLBAR_INFO
*infoPtr
, TBUTTON_INFO
*btnPtr
,
124 HDC hdc
, INT x
, INT y
)
126 /* FIXME: this function is a hack since it uses image list
127 internals directly */
129 HIMAGELIST himl
= infoPtr
->himlDef
;
137 /* create new dc's */
138 hdcImageList
= CreateCompatibleDC (0);
139 hdcMask
= CreateCompatibleDC (0);
141 /* create new bitmap */
142 hbmMask
= CreateBitmap (himl
->cx
, himl
->cy
, 1, 1, NULL
);
143 SelectObject (hdcMask
, hbmMask
);
145 /* copy the mask bitmap */
146 SelectObject (hdcImageList
, himl
->hbmMask
);
147 SetBkColor (hdcImageList
, RGB(255, 255, 255));
148 SetTextColor (hdcImageList
, RGB(0, 0, 0));
149 BitBlt (hdcMask
, 0, 0, himl
->cx
, himl
->cy
,
150 hdcImageList
, himl
->cx
* btnPtr
->iBitmap
, 0, SRCCOPY
);
153 /* add white mask from image */
154 SelectObject (hdcImageList
, himl
->hbmImage
);
155 SetBkColor (hdcImageList
, RGB(0, 0, 0));
156 BitBlt (hdcMask
, 0, 0, himl
->cx
, himl
->cy
,
157 hdcImageList
, himl
->cx
* btnPtr
->iBitmap
, 0, MERGEPAINT
);
160 /* draw the new mask */
161 SelectObject (hdc
, GetSysColorBrush (COLOR_3DHILIGHT
));
162 BitBlt (hdc
, x
+1, y
+1, himl
->cx
, himl
->cy
,
163 hdcMask
, 0, 0, 0xB8074A);
165 SelectObject (hdc
, GetSysColorBrush (COLOR_3DSHADOW
));
166 BitBlt (hdc
, x
, y
, himl
->cx
, himl
->cy
,
167 hdcMask
, 0, 0, 0xB8074A);
169 DeleteObject (hbmMask
);
171 DeleteDC (hdcImageList
);
176 TOOLBAR_DrawButton (HWND hwnd
, TBUTTON_INFO
*btnPtr
, HDC hdc
)
178 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
179 DWORD dwStyle
= GetWindowLongA (hwnd
, GWL_STYLE
);
182 if (btnPtr
->fsState
& TBSTATE_HIDDEN
)
188 if (btnPtr
->fsStyle
& TBSTYLE_SEP
) {
189 if ((dwStyle
& TBSTYLE_FLAT
) && (btnPtr
->iBitmap
== 0))
190 TOOLBAR_DrawFlatSeparator (&rc
, hdc
);
195 if (!(btnPtr
->fsState
& TBSTATE_ENABLED
)) {
196 if (!(dwStyle
& TBSTYLE_FLAT
))
197 DrawEdge (hdc
, &rc
, EDGE_RAISED
,
198 BF_SOFT
| BF_RECT
| BF_MIDDLE
| BF_ADJUST
);
200 if (infoPtr
->himlDis
)
201 ImageList_Draw (infoPtr
->himlDis
, btnPtr
->iBitmap
, hdc
,
202 rc
.left
+1, rc
.top
+1, ILD_NORMAL
);
204 TOOLBAR_DrawMasked (infoPtr
, btnPtr
, hdc
, rc
.left
+1, rc
.top
+1);
206 TOOLBAR_DrawString (infoPtr
, btnPtr
, hdc
, btnPtr
->fsState
);
210 /* pressed TBSTYLE_BUTTON */
211 if (btnPtr
->fsState
& TBSTATE_PRESSED
) {
212 DrawEdge (hdc
, &rc
, EDGE_SUNKEN
, BF_RECT
| BF_MIDDLE
| BF_ADJUST
);
213 ImageList_Draw (infoPtr
->himlDef
, btnPtr
->iBitmap
, hdc
,
214 rc
.left
+2, rc
.top
+2, ILD_NORMAL
);
215 TOOLBAR_DrawString (infoPtr
, btnPtr
, hdc
, btnPtr
->fsState
);
219 /* checked TBSTYLE_CHECK */
220 if ((btnPtr
->fsStyle
& TBSTYLE_CHECK
) &&
221 (btnPtr
->fsState
& TBSTATE_CHECKED
)) {
222 if (dwStyle
& TBSTYLE_FLAT
)
223 DrawEdge (hdc
, &rc
, BDR_SUNKENOUTER
,
224 BF_RECT
| BF_MIDDLE
| BF_ADJUST
);
226 DrawEdge (hdc
, &rc
, EDGE_SUNKEN
,
227 BF_RECT
| BF_MIDDLE
| BF_ADJUST
);
229 TOOLBAR_DrawPattern (hdc
, &rc
);
231 ImageList_Draw (infoPtr
->himlDef
, btnPtr
->iBitmap
, hdc
,
232 rc
.left
+2, rc
.top
+2, ILD_NORMAL
);
234 TOOLBAR_DrawString (infoPtr
, btnPtr
, hdc
, btnPtr
->fsState
);
239 if (btnPtr
->fsState
& TBSTATE_INDETERMINATE
) {
240 DrawEdge (hdc
, &rc
, EDGE_RAISED
,
241 BF_SOFT
| BF_RECT
| BF_MIDDLE
| BF_ADJUST
);
243 TOOLBAR_DrawPattern (hdc
, &rc
);
244 TOOLBAR_DrawMasked (infoPtr
, btnPtr
, hdc
, rc
.left
+1, rc
.top
+1);
245 TOOLBAR_DrawString (infoPtr
, btnPtr
, hdc
, btnPtr
->fsState
);
250 if (dwStyle
& TBSTYLE_FLAT
)
253 DrawEdge (hdc
, &rc
, BDR_RAISEDINNER
,
254 BF_RECT
| BF_MIDDLE
| BF_SOFT
);
255 if (btnPtr
->bHot
&& infoPtr
->himlHot
)
256 ImageList_Draw (infoPtr
->himlHot
, btnPtr
->iBitmap
, hdc
,
257 rc
.left
+2, rc
.top
+2, ILD_NORMAL
);
259 ImageList_Draw (infoPtr
->himlDef
, btnPtr
->iBitmap
, hdc
,
260 rc
.left
+2, rc
.top
+2, ILD_NORMAL
);
264 DrawEdge (hdc
, &rc
, EDGE_RAISED
,
265 BF_SOFT
| BF_RECT
| BF_MIDDLE
| BF_ADJUST
);
267 ImageList_Draw (infoPtr
->himlDef
, btnPtr
->iBitmap
, hdc
,
268 rc
.left
+1, rc
.top
+1, ILD_NORMAL
);
271 TOOLBAR_DrawString (infoPtr
, btnPtr
, hdc
, btnPtr
->fsState
);
276 TOOLBAR_Refresh (HWND hwnd
, HDC hdc
)
278 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
279 TBUTTON_INFO
*btnPtr
;
283 btnPtr
= infoPtr
->buttons
;
284 for (i
= 0; i
< infoPtr
->nNumButtons
; i
++, btnPtr
++)
285 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
290 TOOLBAR_CalcStrings (HWND hwnd
, LPSIZE lpSize
)
292 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
293 TBUTTON_INFO
*btnPtr
;
302 hOldFont
= SelectObject (hdc
, infoPtr
->hFont
);
304 btnPtr
= infoPtr
->buttons
;
305 for (i
= 0; i
< infoPtr
->nNumButtons
; i
++, btnPtr
++) {
306 if (!(btnPtr
->fsState
& TBSTATE_HIDDEN
) &&
307 (btnPtr
->iString
> -1) &&
308 (btnPtr
->iString
< infoPtr
->nNumStrings
)) {
309 LPWSTR lpText
= infoPtr
->strings
[btnPtr
->iString
];
310 GetTextExtentPoint32W (hdc
, lpText
, lstrlenW (lpText
), &sz
);
311 if (sz
.cx
> lpSize
->cx
)
313 if (sz
.cy
> lpSize
->cy
)
318 SelectObject (hdc
, hOldFont
);
321 TRACE("string size %d x %d!\n", lpSize
->cx
, lpSize
->cy
);
324 /***********************************************************************
325 * TOOLBAR_WrapToolbar
327 * This function walks through the buttons and seperators in the
328 * toolbar, and sets the TBSTATE_WRAP flag only on those items where
329 * wrapping should occur based on the width of the toolbar window.
330 * It does *not* calculate button placement itself. That task
331 * takes place in TOOLBAR_CalcToolbar. If the program wants to manage
332 * the toolbar wrapping on it's own, it can use the TBSTYLE_WRAPPABLE
333 * flag, and set the TBSTATE_WRAP flags manually on the appropriate items.
337 TOOLBAR_WrapToolbar( HWND hwnd
)
339 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
340 TBUTTON_INFO
*btnPtr
;
341 DWORD dwStyle
= GetWindowLongA (hwnd
, GWL_STYLE
);
344 BOOL bWrap
, bButtonWrap
;
346 /* When the toolbar window style is not TBSTYLE_WRAPABLE, */
347 /* no layout is necessary. Applications may use this style */
348 /* to perform their own layout on the toolbar. */
349 if( !(dwStyle
& TBSTYLE_WRAPABLE
) )
352 btnPtr
= infoPtr
->buttons
;
353 x
= infoPtr
->nIndent
;
355 GetClientRect( GetParent(hwnd
), &rc
);
356 infoPtr
->nWidth
= rc
.right
- rc
.left
;
359 for (i
= 0; i
< infoPtr
->nNumButtons
; i
++ )
362 btnPtr
[i
].fsState
&= ~TBSTATE_WRAP
;
364 if (btnPtr
[i
].fsState
& TBSTATE_HIDDEN
)
367 /* UNDOCUMENTED: If a separator has a non zero bitmap index, */
368 /* it is the actual width of the separator. This is used for */
369 /* custom controls in toolbars. */
370 if (btnPtr
[i
].fsStyle
& TBSTYLE_SEP
)
371 cx
= (btnPtr
[i
].iBitmap
> 0) ?
372 btnPtr
[i
].iBitmap
: SEPARATOR_WIDTH
;
374 cx
= infoPtr
->nButtonWidth
;
376 /* Two or more adjacent separators form a separator group. */
377 /* The first separator in a group should be wrapped to the */
378 /* next row if the previous wrapping is on a button. */
380 (btnPtr
[i
].fsStyle
& TBSTYLE_SEP
) &&
381 (i
+ 1 < infoPtr
->nNumButtons
) &&
382 (btnPtr
[i
+ 1].fsStyle
& TBSTYLE_SEP
) )
384 btnPtr
[i
].fsState
|= TBSTATE_WRAP
;
385 x
= infoPtr
->nIndent
;
391 /* The layout makes sure the bitmap is visible, but not the button. */
392 if ( x
+ cx
- (infoPtr
->nButtonWidth
- infoPtr
->nBitmapWidth
) / 2
397 /* If the current button is a separator and not hidden, */
398 /* go to the next until it reaches a non separator. */
399 /* Wrap the last separator if it is before a button. */
400 while( ( (btnPtr
[i
].fsStyle
& TBSTYLE_SEP
) ||
401 (btnPtr
[i
].fsState
& TBSTATE_HIDDEN
) ) &&
402 i
< infoPtr
->nNumButtons
)
408 if( bFound
&& i
< infoPtr
->nNumButtons
)
411 btnPtr
[i
].fsState
|= TBSTATE_WRAP
;
412 x
= infoPtr
->nIndent
;
416 else if ( i
>= infoPtr
->nNumButtons
)
419 /* If the current button is not a separator, find the last */
420 /* separator and wrap it. */
421 for ( j
= i
- 1; j
>= 0 && !(btnPtr
[j
].fsState
& TBSTATE_WRAP
); j
--)
423 if ((btnPtr
[j
].fsStyle
& TBSTYLE_SEP
) &&
424 !(btnPtr
[j
].fsState
& TBSTATE_HIDDEN
))
428 x
= infoPtr
->nIndent
;
429 btnPtr
[j
].fsState
|= TBSTATE_WRAP
;
435 /* If no separator available for wrapping, wrap one of */
436 /* non-hidden previous button. */
440 j
>= 0 && !(btnPtr
[j
].fsState
& TBSTATE_WRAP
); j
--)
442 if (btnPtr
[j
].fsState
& TBSTATE_HIDDEN
)
447 x
= infoPtr
->nIndent
;
448 btnPtr
[j
].fsState
|= TBSTATE_WRAP
;
454 /* If all above failed, wrap the current button. */
457 btnPtr
[i
].fsState
|= TBSTATE_WRAP
;
459 x
= infoPtr
->nIndent
;
460 if (btnPtr
[i
].fsState
& TBSTYLE_SEP
)
471 /***********************************************************************
472 * TOOLBAR_CalcToolbar
474 * This function calculates button and separator placement. It first
475 * calculates the button sizes, gets the toolbar window width and then
476 * calls TOOLBAR_WrapToolbar to determine which buttons we need to wrap
477 * on. It assigns a new location to each item and sends this location to
478 * the tooltip window if appropriate. Finally, it updates the rcBound
479 * rect and calculates the new required toolbar window height.
483 TOOLBAR_CalcToolbar (HWND hwnd
)
485 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr(hwnd
);
486 TBUTTON_INFO
*btnPtr
;
487 INT i
, nRows
, nSepRows
;
493 TOOLBAR_CalcStrings (hwnd
, &sizeString
);
495 if (sizeString
.cy
> 0)
496 infoPtr
->nButtonHeight
= sizeString
.cy
+ infoPtr
->nBitmapHeight
+ 6;
497 else if (infoPtr
->nButtonHeight
< infoPtr
->nBitmapHeight
+ 6)
498 infoPtr
->nButtonHeight
= infoPtr
->nBitmapHeight
+ 6;
500 if (sizeString
.cx
> infoPtr
->nBitmapWidth
)
501 infoPtr
->nButtonWidth
= sizeString
.cx
+ 6;
502 else if (infoPtr
->nButtonWidth
< infoPtr
->nBitmapWidth
+ 6)
503 infoPtr
->nButtonWidth
= infoPtr
->nBitmapWidth
+ 6;
505 TOOLBAR_WrapToolbar( hwnd
);
507 x
= infoPtr
->nIndent
;
509 cx
= infoPtr
->nButtonWidth
;
510 cy
= infoPtr
->nButtonHeight
;
511 nRows
= nSepRows
= 0;
513 infoPtr
->rcBound
.top
= y
;
514 infoPtr
->rcBound
.left
= x
;
515 infoPtr
->rcBound
.bottom
= y
+ cy
;
516 infoPtr
->rcBound
.right
= x
;
518 btnPtr
= infoPtr
->buttons
;
519 GetClientRect( GetParent(hwnd
), &rc
);
520 infoPtr
->nWidth
= rc
.right
- rc
.left
;
522 for (i
= 0; i
< infoPtr
->nNumButtons
; i
++, btnPtr
++ )
525 if (btnPtr
->fsState
& TBSTATE_HIDDEN
)
527 SetRectEmpty (&btnPtr
->rect
);
531 /* UNDOCUMENTED: If a separator has a non zero bitmap index, */
532 /* it is the actual width of the separator. This is used for */
533 /* custom controls in toolbars. */
534 if (btnPtr
->fsStyle
& TBSTYLE_SEP
)
535 cx
= (btnPtr
->iBitmap
> 0) ?
536 btnPtr
->iBitmap
: SEPARATOR_WIDTH
;
538 cx
= infoPtr
->nButtonWidth
;
540 if (btnPtr
->fsState
& TBSTATE_WRAP
)
543 SetRect (&btnPtr
->rect
, x
, y
, x
+ cx
, y
+ cy
);
545 if (infoPtr
->rcBound
.left
> x
)
546 infoPtr
->rcBound
.left
= x
;
547 if (infoPtr
->rcBound
.right
< x
+ cx
)
548 infoPtr
->rcBound
.right
= x
+ cx
;
549 if (infoPtr
->rcBound
.bottom
< y
+ cy
)
550 infoPtr
->rcBound
.bottom
= y
+ cy
;
552 /* Set the toolTip only for non-hidden, non-separator button */
553 if (infoPtr
->hwndToolTip
&& !(btnPtr
->fsStyle
& TBSTYLE_SEP
))
557 ZeroMemory (&ti
, sizeof(TTTOOLINFOA
));
558 ti
.cbSize
= sizeof(TTTOOLINFOA
);
560 ti
.uId
= btnPtr
->idCommand
;
561 ti
.rect
= btnPtr
->rect
;
562 SendMessageA (infoPtr
->hwndToolTip
, TTM_NEWTOOLRECTA
,
566 /* btnPtr->nRow is zero based. The space between the rows is */
567 /* also considered as a row. */
568 btnPtr
->nRow
= nRows
+ nSepRows
;
571 if ( !(btnPtr
->fsStyle
& TBSTYLE_SEP
) )
575 /* UNDOCUMENTED: If a separator has a non zero bitmap index, */
576 /* it is the actual width of the separator. This is used for */
577 /* custom controls in toolbars. */
578 y
+= cy
+ ( (btnPtr
->iBitmap
> 0 ) ?
579 btnPtr
->iBitmap
: SEPARATOR_WIDTH
) * 2 /3;
581 /* nSepRows is used to calculate the extra height follwoing */
585 x
= infoPtr
->nIndent
;
592 /* infoPtr->nRows is the number of rows on the toolbar */
593 infoPtr
->nRows
= nRows
+ nSepRows
+ 1;
595 /* nSepRows * (infoPtr->nBitmapHeight + 1) is the space following */
597 infoPtr
->nHeight
= TOP_BORDER
+ (nRows
+ 1) * infoPtr
->nButtonHeight
+
598 nSepRows
* SEPARATOR_WIDTH
* 2 / 3 +
599 nSepRows
* (infoPtr
->nBitmapHeight
+ 1) +
601 TRACE("toolbar height %d\n", infoPtr
->nHeight
);
606 TOOLBAR_InternalHitTest (HWND hwnd
, LPPOINT lpPt
)
608 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
609 TBUTTON_INFO
*btnPtr
;
612 btnPtr
= infoPtr
->buttons
;
613 for (i
= 0; i
< infoPtr
->nNumButtons
; i
++, btnPtr
++) {
614 if (btnPtr
->fsState
& TBSTATE_HIDDEN
)
617 if (btnPtr
->fsStyle
& TBSTYLE_SEP
) {
618 if (PtInRect (&btnPtr
->rect
, *lpPt
)) {
619 TRACE(" ON SEPARATOR %d!\n", i
);
624 if (PtInRect (&btnPtr
->rect
, *lpPt
)) {
625 TRACE(" ON BUTTON %d!\n", i
);
631 TRACE(" NOWHERE!\n");
637 TOOLBAR_GetButtonIndex (TOOLBAR_INFO
*infoPtr
, INT idCommand
)
639 TBUTTON_INFO
*btnPtr
;
642 btnPtr
= infoPtr
->buttons
;
643 for (i
= 0; i
< infoPtr
->nNumButtons
; i
++, btnPtr
++) {
644 if (btnPtr
->idCommand
== idCommand
) {
645 TRACE("command=%d index=%d\n", idCommand
, i
);
649 TRACE("no index found for command=%d\n", idCommand
);
655 TOOLBAR_GetCheckedGroupButtonIndex (TOOLBAR_INFO
*infoPtr
, INT nIndex
)
657 TBUTTON_INFO
*btnPtr
;
660 if ((nIndex
< 0) || (nIndex
> infoPtr
->nNumButtons
))
663 /* check index button */
664 btnPtr
= &infoPtr
->buttons
[nIndex
];
665 if ((btnPtr
->fsStyle
& TBSTYLE_CHECKGROUP
) == TBSTYLE_CHECKGROUP
) {
666 if (btnPtr
->fsState
& TBSTATE_CHECKED
)
670 /* check previous buttons */
671 nRunIndex
= nIndex
- 1;
672 while (nRunIndex
>= 0) {
673 btnPtr
= &infoPtr
->buttons
[nRunIndex
];
674 if ((btnPtr
->fsStyle
& TBSTYLE_CHECKGROUP
) == TBSTYLE_CHECKGROUP
) {
675 if (btnPtr
->fsState
& TBSTATE_CHECKED
)
683 /* check next buttons */
684 nRunIndex
= nIndex
+ 1;
685 while (nRunIndex
< infoPtr
->nNumButtons
) {
686 btnPtr
= &infoPtr
->buttons
[nRunIndex
];
687 if ((btnPtr
->fsStyle
& TBSTYLE_CHECKGROUP
) == TBSTYLE_CHECKGROUP
) {
688 if (btnPtr
->fsState
& TBSTATE_CHECKED
)
701 TOOLBAR_RelayEvent (HWND hwndTip
, HWND hwndMsg
, UINT uMsg
,
702 WPARAM wParam
, LPARAM lParam
)
710 msg
.time
= GetMessageTime ();
711 msg
.pt
.x
= LOWORD(GetMessagePos ());
712 msg
.pt
.y
= HIWORD(GetMessagePos ());
714 SendMessageA (hwndTip
, TTM_RELAYEVENT
, 0, (LPARAM
)&msg
);
718 /***********************************************************************
719 * TOOLBAR_CustomizeDialogProc
720 * This function implements the toolbar customization dialog.
723 TOOLBAR_CustomizeDialogProc(HWND hwnd
, UINT uMsg
, WPARAM wParam
, LPARAM lParam
)
725 TOOLBAR_INFO
*infoPtr
= (TOOLBAR_INFO
*)GetWindowLongA (hwnd
, DWL_USER
);
726 static HDSA hDsa
= NULL
;
731 infoPtr
= (TOOLBAR_INFO
*)lParam
;
732 SetWindowLongA (hwnd
, DWL_USER
, (DWORD
)infoPtr
);
734 hDsa
= DSA_Create (sizeof(TBUTTON_INFO
), 5);
738 TBUTTON_INFO
*btnPtr
;
741 /* insert 'virtual' separator button into 'available buttons' list */
742 SendDlgItemMessageA (hwnd
, IDC_AVAILBTN_LBOX
, LB_ADDSTRING
, 0, (LPARAM
)"");
744 /* copy all buttons and append them to the right listbox */
745 btnPtr
= infoPtr
->buttons
;
746 for (i
= 0; i
< infoPtr
->nNumButtons
; i
++, btnPtr
++)
748 DSA_InsertItem (hDsa
, i
, btnPtr
);
750 /* FIXME: hidden buttons appear in the 'toolbar buttons' list too */
751 if (btnPtr
->fsState
& TBSTATE_HIDDEN
)
753 SendDlgItemMessageA (hwnd
, IDC_AVAILBTN_LBOX
, LB_ADDSTRING
, 0, (LPARAM
)"");
757 SendDlgItemMessageA (hwnd
, IDC_TOOLBARBTN_LBOX
, LB_ADDSTRING
, 0, (LPARAM
)"");
761 /* append 'virtual' separator button to the 'toolbar buttons' list */
767 EndDialog(hwnd
, FALSE
);
771 switch (LOWORD(wParam
))
774 EndDialog(hwnd
, FALSE
);
785 if (wParam
== IDC_AVAILBTN_LBOX
|| wParam
== IDC_TOOLBARBTN_LBOX
)
787 LPDRAWITEMSTRUCT lpdis
= (LPDRAWITEMSTRUCT
)lParam
;
792 COLORREF oldText
= 0;
795 FIXME("action: %x itemState: %x\n",
796 lpdis
->itemAction
, lpdis
->itemState
);
798 if (lpdis
->itemState
& ODS_FOCUS
)
800 oldBk
= SetBkColor (lpdis
->hDC
, GetSysColor(COLOR_HIGHLIGHT
));
801 oldText
= SetTextColor (lpdis
->hDC
, GetSysColor(COLOR_HIGHLIGHTTEXT
));
804 hOldPen
= SelectObject (lpdis
->hDC
, GetSysColorPen ((lpdis
->itemState
& ODS_SELECTED
)?COLOR_HIGHLIGHT
:COLOR_WINDOW
));
805 hOldBrush
= SelectObject (lpdis
->hDC
, GetSysColorBrush ((lpdis
->itemState
& ODS_FOCUS
)?COLOR_HIGHLIGHT
:COLOR_WINDOW
));
807 /* fill background rectangle */
808 Rectangle (lpdis
->hDC
, lpdis
->rcItem
.left
, lpdis
->rcItem
.top
,
809 lpdis
->rcItem
.right
, lpdis
->rcItem
.bottom
);
811 /* calculate button and text rectangles */
812 CopyRect (&rcButton
, &lpdis
->rcItem
);
813 InflateRect (&rcButton
, -1, -1);
814 CopyRect (&rcText
, &rcButton
);
815 rcButton
.right
= rcButton
.left
+ infoPtr
->nBitmapWidth
+ 6;
816 rcText
.left
= rcButton
.right
+ 2;
818 /* draw focus rectangle */
819 if (lpdis
->itemState
& ODS_FOCUS
)
820 DrawFocusRect (lpdis
->hDC
, &lpdis
->rcItem
);
823 DrawEdge (lpdis
->hDC
, &rcButton
, EDGE_RAISED
, BF_RECT
|BF_MIDDLE
|BF_SOFT
);
825 /* FIXME: draw bitmap */
827 ImageList_Draw (infoPtr->himlStd, btnPtr->iBitmap, hdc,
828 rcButton.left+1, rcButton.top+1, ILD_NORMAL);
831 if (wParam
== IDC_AVAILBTN_LBOX
&& lpdis
->itemID
== 0)
833 /* virtual separator in the 'available' list */
834 DrawTextA (lpdis
->hDC
, "Separator", -1, &rcText
,
835 DT_LEFT
| DT_VCENTER
| DT_SINGLELINE
);
842 if (lpdis
->itemState
& ODS_FOCUS
)
844 SetBkColor (lpdis
->hDC
, oldBk
);
845 SetTextColor (lpdis
->hDC
, oldText
);
848 SelectObject (lpdis
->hDC
, hOldBrush
);
849 SelectObject (lpdis
->hDC
, hOldPen
);
856 if (wParam
== IDC_AVAILBTN_LBOX
|| wParam
== IDC_TOOLBARBTN_LBOX
)
858 MEASUREITEMSTRUCT
*lpmis
= (MEASUREITEMSTRUCT
*)lParam
;
861 lpmis
->itemHeight
= infoPtr
->nBitmapHeight
+ 8;
863 lpmis
->itemHeight
= 16 + 8; /* default height */
875 /***********************************************************************
876 * TOOLBAR_AddBitmap: Add the bitmaps to the default image list.
880 TOOLBAR_AddBitmap (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
882 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
883 LPTBADDBITMAP lpAddBmp
= (LPTBADDBITMAP
)lParam
;
884 INT nIndex
= 0, nButtons
;
890 if (lpAddBmp
->hInst
== HINST_COMMCTRL
)
892 if ((lpAddBmp
->nID
& ~1) == IDB_STD_SMALL_COLOR
)
894 else if ((lpAddBmp
->nID
& ~1) == IDB_VIEW_SMALL_COLOR
)
896 else if ((lpAddBmp
->nID
& ~1) == IDB_HIST_SMALL_COLOR
)
901 TRACE ("adding %d internal bitmaps!\n", nButtons
);
903 /* Windows resize all the buttons to the size of a newly added standard image */
904 if (lpAddBmp
->nID
& 1)
907 SendMessageA (hwnd
, TB_SETBITMAPSIZE
, 0,
908 MAKELPARAM((WORD
)26, (WORD
)26));
909 SendMessageA (hwnd
, TB_SETBUTTONSIZE
, 0,
910 MAKELPARAM((WORD
)33, (WORD
)33));
915 SendMessageA (hwnd
, TB_SETBITMAPSIZE
, 0,
916 MAKELPARAM((WORD
)16, (WORD
)16));
917 SendMessageA (hwnd
, TB_SETBUTTONSIZE
, 0,
918 MAKELPARAM((WORD
)22, (WORD
)22));
921 TOOLBAR_CalcToolbar (hwnd
);
925 nButtons
= (INT
)wParam
;
929 TRACE ("adding %d bitmaps!\n", nButtons
);
932 if (!(infoPtr
->himlDef
)) {
933 /* create new default image list */
934 TRACE ("creating default image list!\n");
937 ImageList_Create (infoPtr
->nBitmapWidth
, infoPtr
->nBitmapHeight
,
938 ILC_COLOR
| ILC_MASK
, nButtons
, 2);
939 infoPtr
->himlInt
= infoPtr
->himlDef
;
942 /* Add bitmaps to the default image list */
943 if (lpAddBmp
->hInst
== (HINSTANCE
)0)
946 ImageList_AddMasked (infoPtr
->himlDef
, (HBITMAP
)lpAddBmp
->nID
,
949 else if (lpAddBmp
->hInst
== HINST_COMMCTRL
)
951 /* Add system bitmaps */
952 switch (lpAddBmp
->nID
)
954 case IDB_STD_SMALL_COLOR
:
955 hbmLoad
= LoadBitmapA (COMCTL32_hModule
,
956 MAKEINTRESOURCEA(IDB_STD_SMALL
));
957 nIndex
= ImageList_AddMasked (infoPtr
->himlDef
,
958 hbmLoad
, CLR_DEFAULT
);
959 DeleteObject (hbmLoad
);
962 case IDB_STD_LARGE_COLOR
:
963 hbmLoad
= LoadBitmapA (COMCTL32_hModule
,
964 MAKEINTRESOURCEA(IDB_STD_LARGE
));
965 nIndex
= ImageList_AddMasked (infoPtr
->himlDef
,
966 hbmLoad
, CLR_DEFAULT
);
967 DeleteObject (hbmLoad
);
970 case IDB_VIEW_SMALL_COLOR
:
971 hbmLoad
= LoadBitmapA (COMCTL32_hModule
,
972 MAKEINTRESOURCEA(IDB_VIEW_SMALL
));
973 nIndex
= ImageList_AddMasked (infoPtr
->himlDef
,
974 hbmLoad
, CLR_DEFAULT
);
975 DeleteObject (hbmLoad
);
978 case IDB_VIEW_LARGE_COLOR
:
979 hbmLoad
= LoadBitmapA (COMCTL32_hModule
,
980 MAKEINTRESOURCEA(IDB_VIEW_LARGE
));
981 nIndex
= ImageList_AddMasked (infoPtr
->himlDef
,
982 hbmLoad
, CLR_DEFAULT
);
983 DeleteObject (hbmLoad
);
986 case IDB_HIST_SMALL_COLOR
:
987 hbmLoad
= LoadBitmapA (COMCTL32_hModule
,
988 MAKEINTRESOURCEA(IDB_HIST_SMALL
));
989 nIndex
= ImageList_AddMasked (infoPtr
->himlDef
,
990 hbmLoad
, CLR_DEFAULT
);
991 DeleteObject (hbmLoad
);
994 case IDB_HIST_LARGE_COLOR
:
995 hbmLoad
= LoadBitmapA (COMCTL32_hModule
,
996 MAKEINTRESOURCEA(IDB_HIST_LARGE
));
997 nIndex
= ImageList_AddMasked (infoPtr
->himlDef
,
998 hbmLoad
, CLR_DEFAULT
);
999 DeleteObject (hbmLoad
);
1003 nIndex
= ImageList_GetImageCount (infoPtr
->himlDef
);
1004 ERR ("invalid imagelist!\n");
1010 hbmLoad
= LoadBitmapA (lpAddBmp
->hInst
, (LPSTR
)lpAddBmp
->nID
);
1011 nIndex
= ImageList_AddMasked (infoPtr
->himlDef
, hbmLoad
, CLR_DEFAULT
);
1012 DeleteObject (hbmLoad
);
1015 infoPtr
->nNumBitmaps
+= nButtons
;
1022 TOOLBAR_AddButtonsA (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1024 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1025 LPTBBUTTON lpTbb
= (LPTBBUTTON
)lParam
;
1026 INT nOldButtons
, nNewButtons
, nAddButtons
, nCount
;
1028 TRACE("adding %d buttons!\n", wParam
);
1030 nAddButtons
= (UINT
)wParam
;
1031 nOldButtons
= infoPtr
->nNumButtons
;
1032 nNewButtons
= nOldButtons
+ nAddButtons
;
1034 if (infoPtr
->nNumButtons
== 0) {
1036 COMCTL32_Alloc (sizeof(TBUTTON_INFO
) * nNewButtons
);
1039 TBUTTON_INFO
*oldButtons
= infoPtr
->buttons
;
1041 COMCTL32_Alloc (sizeof(TBUTTON_INFO
) * nNewButtons
);
1042 memcpy (&infoPtr
->buttons
[0], &oldButtons
[0],
1043 nOldButtons
* sizeof(TBUTTON_INFO
));
1044 COMCTL32_Free (oldButtons
);
1047 infoPtr
->nNumButtons
= nNewButtons
;
1049 /* insert new button data */
1050 for (nCount
= 0; nCount
< nAddButtons
; nCount
++) {
1051 TBUTTON_INFO
*btnPtr
= &infoPtr
->buttons
[nOldButtons
+nCount
];
1052 btnPtr
->iBitmap
= lpTbb
[nCount
].iBitmap
;
1053 btnPtr
->idCommand
= lpTbb
[nCount
].idCommand
;
1054 btnPtr
->fsState
= lpTbb
[nCount
].fsState
;
1055 btnPtr
->fsStyle
= lpTbb
[nCount
].fsStyle
;
1056 btnPtr
->dwData
= lpTbb
[nCount
].dwData
;
1057 btnPtr
->iString
= lpTbb
[nCount
].iString
;
1058 btnPtr
->bHot
= FALSE
;
1060 if ((infoPtr
->hwndToolTip
) && !(btnPtr
->fsStyle
& TBSTYLE_SEP
)) {
1063 ZeroMemory (&ti
, sizeof(TTTOOLINFOA
));
1064 ti
.cbSize
= sizeof (TTTOOLINFOA
);
1066 ti
.uId
= btnPtr
->idCommand
;
1068 ti
.lpszText
= LPSTR_TEXTCALLBACKA
;
1070 SendMessageA (infoPtr
->hwndToolTip
, TTM_ADDTOOLA
,
1075 TOOLBAR_CalcToolbar (hwnd
);
1077 InvalidateRect(hwnd
, NULL
, FALSE
);
1083 /* << TOOLBAR_AddButtons32W >> */
1087 TOOLBAR_AddStringA (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1089 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1092 if ((wParam
) && (HIWORD(lParam
) == 0)) {
1095 TRACE("adding string from resource!\n");
1097 len
= LoadStringA ((HINSTANCE
)wParam
, (UINT
)lParam
,
1100 TRACE("len=%d \"%s\"\n", len
, szString
);
1101 nIndex
= infoPtr
->nNumStrings
;
1102 if (infoPtr
->nNumStrings
== 0) {
1104 COMCTL32_Alloc (sizeof(LPWSTR
));
1107 LPWSTR
*oldStrings
= infoPtr
->strings
;
1109 COMCTL32_Alloc (sizeof(LPWSTR
) * (infoPtr
->nNumStrings
+ 1));
1110 memcpy (&infoPtr
->strings
[0], &oldStrings
[0],
1111 sizeof(LPWSTR
) * infoPtr
->nNumStrings
);
1112 COMCTL32_Free (oldStrings
);
1115 infoPtr
->strings
[infoPtr
->nNumStrings
] =
1116 COMCTL32_Alloc (sizeof(WCHAR
)*(len
+1));
1117 lstrcpyAtoW (infoPtr
->strings
[infoPtr
->nNumStrings
], szString
);
1118 infoPtr
->nNumStrings
++;
1121 LPSTR p
= (LPSTR
)lParam
;
1126 TRACE("adding string(s) from array!\n");
1127 nIndex
= infoPtr
->nNumStrings
;
1130 TRACE("len=%d \"%s\"\n", len
, p
);
1132 if (infoPtr
->nNumStrings
== 0) {
1134 COMCTL32_Alloc (sizeof(LPWSTR
));
1137 LPWSTR
*oldStrings
= infoPtr
->strings
;
1139 COMCTL32_Alloc (sizeof(LPWSTR
) * (infoPtr
->nNumStrings
+ 1));
1140 memcpy (&infoPtr
->strings
[0], &oldStrings
[0],
1141 sizeof(LPWSTR
) * infoPtr
->nNumStrings
);
1142 COMCTL32_Free (oldStrings
);
1145 infoPtr
->strings
[infoPtr
->nNumStrings
] =
1146 COMCTL32_Alloc (sizeof(WCHAR
)*(len
+1));
1147 lstrcpyAtoW (infoPtr
->strings
[infoPtr
->nNumStrings
], p
);
1148 infoPtr
->nNumStrings
++;
1159 TOOLBAR_AddStringW (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1161 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1164 if ((wParam
) && (HIWORD(lParam
) == 0)) {
1165 WCHAR szString
[256];
1167 TRACE("adding string from resource!\n");
1169 len
= LoadStringW ((HINSTANCE
)wParam
, (UINT
)lParam
,
1172 TRACE("len=%d \"%s\"\n", len
, debugstr_w(szString
));
1173 nIndex
= infoPtr
->nNumStrings
;
1174 if (infoPtr
->nNumStrings
== 0) {
1176 COMCTL32_Alloc (sizeof(LPWSTR
));
1179 LPWSTR
*oldStrings
= infoPtr
->strings
;
1181 COMCTL32_Alloc (sizeof(LPWSTR
) * (infoPtr
->nNumStrings
+ 1));
1182 memcpy (&infoPtr
->strings
[0], &oldStrings
[0],
1183 sizeof(LPWSTR
) * infoPtr
->nNumStrings
);
1184 COMCTL32_Free (oldStrings
);
1187 infoPtr
->strings
[infoPtr
->nNumStrings
] =
1188 COMCTL32_Alloc (sizeof(WCHAR
)*(len
+1));
1189 lstrcpyW (infoPtr
->strings
[infoPtr
->nNumStrings
], szString
);
1190 infoPtr
->nNumStrings
++;
1193 LPWSTR p
= (LPWSTR
)lParam
;
1198 TRACE("adding string(s) from array!\n");
1199 nIndex
= infoPtr
->nNumStrings
;
1202 TRACE("len=%d \"%s\"\n", len
, debugstr_w(p
));
1204 if (infoPtr
->nNumStrings
== 0) {
1206 COMCTL32_Alloc (sizeof(LPWSTR
));
1209 LPWSTR
*oldStrings
= infoPtr
->strings
;
1211 COMCTL32_Alloc (sizeof(LPWSTR
) * (infoPtr
->nNumStrings
+ 1));
1212 memcpy (&infoPtr
->strings
[0], &oldStrings
[0],
1213 sizeof(LPWSTR
) * infoPtr
->nNumStrings
);
1214 COMCTL32_Free (oldStrings
);
1217 infoPtr
->strings
[infoPtr
->nNumStrings
] =
1218 COMCTL32_Alloc (sizeof(WCHAR
)*(len
+1));
1219 lstrcpyW (infoPtr
->strings
[infoPtr
->nNumStrings
], p
);
1220 infoPtr
->nNumStrings
++;
1231 TOOLBAR_AutoSize (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1233 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1234 DWORD dwStyle
= GetWindowLongA (hwnd
, GWL_STYLE
);
1241 TRACE("resize forced!\n");
1243 parent
= GetParent (hwnd
);
1244 GetClientRect(parent
, &parent_rect
);
1246 if (dwStyle
& CCS_NORESIZE
) {
1247 uPosFlags
|= (SWP_NOSIZE
| SWP_NOMOVE
);
1252 infoPtr
->nWidth
= parent_rect
.right
- parent_rect
.left
;
1253 TOOLBAR_CalcToolbar (hwnd
);
1254 InvalidateRect( hwnd
, NULL
, TRUE
);
1255 cy
= infoPtr
->nHeight
;
1256 cx
= infoPtr
->nWidth
;
1259 if (dwStyle
& CCS_NOPARENTALIGN
)
1260 uPosFlags
|= SWP_NOMOVE
;
1262 if (!(dwStyle
& CCS_NODIVIDER
))
1263 cy
+= GetSystemMetrics(SM_CYEDGE
);
1265 infoPtr
->bAutoSize
= TRUE
;
1266 SetWindowPos (hwnd
, HWND_TOP
, parent_rect
.left
, parent_rect
.top
,
1274 TOOLBAR_ButtonCount (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1276 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1278 return infoPtr
->nNumButtons
;
1283 TOOLBAR_ButtonStructSize (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1285 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1287 if (infoPtr
== NULL
) {
1288 ERR("(0x%x, 0x%x, 0x%lx)\n", hwnd
, wParam
, lParam
);
1289 ERR("infoPtr == NULL!\n");
1293 infoPtr
->dwStructSize
= (DWORD
)wParam
;
1300 TOOLBAR_ChangeBitmap (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1302 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1303 TBUTTON_INFO
*btnPtr
;
1307 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1311 btnPtr
= &infoPtr
->buttons
[nIndex
];
1312 btnPtr
->iBitmap
= LOWORD(lParam
);
1315 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
1316 ReleaseDC (hwnd
, hdc
);
1323 TOOLBAR_CheckButton (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1325 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1326 TBUTTON_INFO
*btnPtr
;
1331 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1335 btnPtr
= &infoPtr
->buttons
[nIndex
];
1337 if (!(btnPtr
->fsStyle
& TBSTYLE_CHECK
))
1340 if (LOWORD(lParam
) == FALSE
)
1341 btnPtr
->fsState
&= ~TBSTATE_CHECKED
;
1343 if (btnPtr
->fsStyle
& TBSTYLE_GROUP
) {
1345 TOOLBAR_GetCheckedGroupButtonIndex (infoPtr
, nIndex
);
1346 if (nOldIndex
== nIndex
)
1348 if (nOldIndex
!= -1)
1349 infoPtr
->buttons
[nOldIndex
].fsState
&= ~TBSTATE_CHECKED
;
1351 btnPtr
->fsState
|= TBSTATE_CHECKED
;
1355 if (nOldIndex
!= -1)
1356 TOOLBAR_DrawButton (hwnd
, &infoPtr
->buttons
[nOldIndex
], hdc
);
1357 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
1358 ReleaseDC (hwnd
, hdc
);
1360 /* FIXME: Send a WM_NOTIFY?? */
1367 TOOLBAR_CommandToIndex (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1369 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1371 return TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1376 TOOLBAR_Customize (HWND hwnd
)
1378 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1384 /* send TBN_BEGINADJUST notification */
1385 nmhdr
.hwndFrom
= hwnd
;
1386 nmhdr
.idFrom
= GetWindowLongA (hwnd
, GWL_ID
);
1387 nmhdr
.code
= TBN_BEGINADJUST
;
1389 SendMessageA (infoPtr
->hwndNotify
, WM_NOTIFY
,
1390 (WPARAM
)nmhdr
.idFrom
, (LPARAM
)&nmhdr
);
1392 if (!(hRes
= FindResourceA (COMCTL32_hModule
,
1393 MAKEINTRESOURCEA(IDD_TBCUSTOMIZE
),
1397 if(!(template = (LPVOID
)LoadResource (COMCTL32_hModule
, hRes
)))
1400 ret
= DialogBoxIndirectParamA (GetWindowLongA (hwnd
, GWL_HINSTANCE
),
1401 (LPDLGTEMPLATEA
)template,
1403 (DLGPROC
)TOOLBAR_CustomizeDialogProc
,
1406 /* send TBN_ENDADJUST notification */
1407 nmhdr
.code
= TBN_ENDADJUST
;
1409 SendMessageA (infoPtr
->hwndNotify
, WM_NOTIFY
,
1410 (WPARAM
)nmhdr
.idFrom
, (LPARAM
)&nmhdr
);
1417 TOOLBAR_DeleteButton (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1419 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1420 INT nIndex
= (INT
)wParam
;
1422 if ((nIndex
< 0) || (nIndex
>= infoPtr
->nNumButtons
))
1425 if ((infoPtr
->hwndToolTip
) &&
1426 !(infoPtr
->buttons
[nIndex
].fsStyle
& TBSTYLE_SEP
)) {
1429 ZeroMemory (&ti
, sizeof(TTTOOLINFOA
));
1430 ti
.cbSize
= sizeof (TTTOOLINFOA
);
1432 ti
.uId
= infoPtr
->buttons
[nIndex
].idCommand
;
1434 SendMessageA (infoPtr
->hwndToolTip
, TTM_DELTOOLA
, 0, (LPARAM
)&ti
);
1437 if (infoPtr
->nNumButtons
== 1) {
1438 TRACE(" simple delete!\n");
1439 COMCTL32_Free (infoPtr
->buttons
);
1440 infoPtr
->buttons
= NULL
;
1441 infoPtr
->nNumButtons
= 0;
1444 TBUTTON_INFO
*oldButtons
= infoPtr
->buttons
;
1445 TRACE("complex delete! [nIndex=%d]\n", nIndex
);
1447 infoPtr
->nNumButtons
--;
1448 infoPtr
->buttons
= COMCTL32_Alloc (sizeof (TBUTTON_INFO
) * infoPtr
->nNumButtons
);
1450 memcpy (&infoPtr
->buttons
[0], &oldButtons
[0],
1451 nIndex
* sizeof(TBUTTON_INFO
));
1454 if (nIndex
< infoPtr
->nNumButtons
) {
1455 memcpy (&infoPtr
->buttons
[nIndex
], &oldButtons
[nIndex
+1],
1456 (infoPtr
->nNumButtons
- nIndex
) * sizeof(TBUTTON_INFO
));
1459 COMCTL32_Free (oldButtons
);
1462 TOOLBAR_CalcToolbar (hwnd
);
1464 InvalidateRect (hwnd
, NULL
, TRUE
);
1471 TOOLBAR_EnableButton (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1473 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1474 TBUTTON_INFO
*btnPtr
;
1478 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1482 btnPtr
= &infoPtr
->buttons
[nIndex
];
1483 if (LOWORD(lParam
) == FALSE
)
1484 btnPtr
->fsState
&= ~(TBSTATE_ENABLED
| TBSTATE_PRESSED
);
1486 btnPtr
->fsState
|= TBSTATE_ENABLED
;
1489 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
1490 ReleaseDC (hwnd
, hdc
);
1496 /* << TOOLBAR_GetAnchorHighlight >> */
1500 TOOLBAR_GetBitmap (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1502 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1505 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1509 return infoPtr
->buttons
[nIndex
].iBitmap
;
1513 static inline LRESULT
1514 TOOLBAR_GetBitmapFlags (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1516 return (GetDeviceCaps (0, LOGPIXELSX
) >= 120) ? TBBF_LARGE
: 0;
1521 TOOLBAR_GetButton (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1523 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1524 LPTBBUTTON lpTbb
= (LPTBBUTTON
)lParam
;
1525 INT nIndex
= (INT
)wParam
;
1526 TBUTTON_INFO
*btnPtr
;
1528 if (infoPtr
== NULL
)
1534 if ((nIndex
< 0) || (nIndex
>= infoPtr
->nNumButtons
))
1537 btnPtr
= &infoPtr
->buttons
[nIndex
];
1538 lpTbb
->iBitmap
= btnPtr
->iBitmap
;
1539 lpTbb
->idCommand
= btnPtr
->idCommand
;
1540 lpTbb
->fsState
= btnPtr
->fsState
;
1541 lpTbb
->fsStyle
= btnPtr
->fsStyle
;
1542 lpTbb
->dwData
= btnPtr
->dwData
;
1543 lpTbb
->iString
= btnPtr
->iString
;
1550 TOOLBAR_GetButtonInfoA (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1552 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1553 LPTBBUTTONINFOA lpTbInfo
= (LPTBBUTTONINFOA
)lParam
;
1554 TBUTTON_INFO
*btnPtr
;
1557 if (infoPtr
== NULL
)
1559 if (lpTbInfo
== NULL
)
1561 if (lpTbInfo
->cbSize
< sizeof(TBBUTTONINFOA
))
1564 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1568 btnPtr
= &infoPtr
->buttons
[nIndex
];
1570 if (lpTbInfo
->dwMask
& TBIF_COMMAND
)
1571 lpTbInfo
->idCommand
= btnPtr
->idCommand
;
1572 if (lpTbInfo
->dwMask
& TBIF_IMAGE
)
1573 lpTbInfo
->iImage
= btnPtr
->iBitmap
;
1574 if (lpTbInfo
->dwMask
& TBIF_LPARAM
)
1575 lpTbInfo
->lParam
= btnPtr
->dwData
;
1576 if (lpTbInfo
->dwMask
& TBIF_SIZE
)
1577 lpTbInfo
->cx
= (WORD
)(btnPtr
->rect
.right
- btnPtr
->rect
.left
);
1578 if (lpTbInfo
->dwMask
& TBIF_STATE
)
1579 lpTbInfo
->fsState
= btnPtr
->fsState
;
1580 if (lpTbInfo
->dwMask
& TBIF_STYLE
)
1581 lpTbInfo
->fsStyle
= btnPtr
->fsStyle
;
1582 if (lpTbInfo
->dwMask
& TBIF_TEXT
) {
1583 if ((btnPtr
->iString
>= 0) || (btnPtr
->iString
< infoPtr
->nNumStrings
))
1584 lstrcpynA (lpTbInfo
->pszText
,
1585 (LPSTR
)infoPtr
->strings
[btnPtr
->iString
],
1593 /* << TOOLBAR_GetButtonInfo32W >> */
1597 TOOLBAR_GetButtonSize (HWND hwnd
)
1599 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1601 return MAKELONG((WORD
)infoPtr
->nButtonWidth
,
1602 (WORD
)infoPtr
->nButtonHeight
);
1607 TOOLBAR_GetButtonTextA (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1609 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1610 INT nIndex
, nStringIndex
;
1612 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1616 nStringIndex
= infoPtr
->buttons
[nIndex
].iString
;
1618 TRACE("index=%d stringIndex=%d\n", nIndex
, nStringIndex
);
1620 if ((nStringIndex
< 0) || (nStringIndex
>= infoPtr
->nNumStrings
))
1623 if (lParam
== 0) return -1;
1625 lstrcpyA ((LPSTR
)lParam
, (LPSTR
)infoPtr
->strings
[nStringIndex
]);
1627 return lstrlenA ((LPSTR
)infoPtr
->strings
[nStringIndex
]);
1631 /* << TOOLBAR_GetButtonText32W >> */
1632 /* << TOOLBAR_GetColorScheme >> */
1636 TOOLBAR_GetDisabledImageList (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1638 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1640 return (LRESULT
)infoPtr
->himlDis
;
1644 inline static LRESULT
1645 TOOLBAR_GetExtendedStyle (HWND hwnd
)
1647 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1649 return infoPtr
->dwExStyle
;
1654 TOOLBAR_GetHotImageList (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1656 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1658 return (LRESULT
)infoPtr
->himlHot
;
1662 /* << TOOLBAR_GetHotItem >> */
1666 TOOLBAR_GetImageList (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1668 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1670 return (LRESULT
)infoPtr
->himlDef
;
1674 /* << TOOLBAR_GetInsertMark >> */
1675 /* << TOOLBAR_GetInsertMarkColor >> */
1679 TOOLBAR_GetItemRect (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1681 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1682 TBUTTON_INFO
*btnPtr
;
1686 if (infoPtr
== NULL
)
1688 nIndex
= (INT
)wParam
;
1689 btnPtr
= &infoPtr
->buttons
[nIndex
];
1690 if ((nIndex
< 0) || (nIndex
>= infoPtr
->nNumButtons
))
1692 lpRect
= (LPRECT
)lParam
;
1695 if (btnPtr
->fsState
& TBSTATE_HIDDEN
)
1698 TOOLBAR_CalcToolbar( hwnd
);
1700 lpRect
->left
= btnPtr
->rect
.left
;
1701 lpRect
->right
= btnPtr
->rect
.right
;
1702 lpRect
->bottom
= btnPtr
->rect
.bottom
;
1703 lpRect
->top
= btnPtr
->rect
.top
;
1710 TOOLBAR_GetMaxSize (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1712 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1713 LPSIZE lpSize
= (LPSIZE
)lParam
;
1718 lpSize
->cx
= infoPtr
->rcBound
.right
- infoPtr
->rcBound
.left
;
1719 lpSize
->cy
= infoPtr
->rcBound
.bottom
- infoPtr
->rcBound
.top
;
1721 TRACE("maximum size %d x %d\n",
1722 infoPtr
->rcBound
.right
- infoPtr
->rcBound
.left
,
1723 infoPtr
->rcBound
.bottom
- infoPtr
->rcBound
.top
);
1729 /* << TOOLBAR_GetObject >> */
1730 /* << TOOLBAR_GetPadding >> */
1734 TOOLBAR_GetRect (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1736 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1737 TBUTTON_INFO
*btnPtr
;
1741 if (infoPtr
== NULL
)
1743 nIndex
= (INT
)wParam
;
1744 btnPtr
= &infoPtr
->buttons
[nIndex
];
1745 if ((nIndex
< 0) || (nIndex
>= infoPtr
->nNumButtons
))
1747 lpRect
= (LPRECT
)lParam
;
1751 lpRect
->left
= btnPtr
->rect
.left
;
1752 lpRect
->right
= btnPtr
->rect
.right
;
1753 lpRect
->bottom
= btnPtr
->rect
.bottom
;
1754 lpRect
->top
= btnPtr
->rect
.top
;
1761 TOOLBAR_GetRows (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1763 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1765 if (GetWindowLongA (hwnd
, GWL_STYLE
) & TBSTYLE_WRAPABLE
)
1766 return infoPtr
->nRows
;
1773 TOOLBAR_GetState (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1775 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1778 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1782 return infoPtr
->buttons
[nIndex
].fsState
;
1787 TOOLBAR_GetStyle (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1789 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1792 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1796 return infoPtr
->buttons
[nIndex
].fsStyle
;
1801 TOOLBAR_GetTextRows (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1803 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1805 if (infoPtr
== NULL
)
1808 return infoPtr
->nMaxTextRows
;
1813 TOOLBAR_GetToolTips (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1815 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1817 if (infoPtr
== NULL
)
1819 return infoPtr
->hwndToolTip
;
1824 TOOLBAR_GetUnicodeFormat (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1826 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1828 TRACE("%s hwnd=0x%x stub!\n",
1829 infoPtr
->bUnicode
? "TRUE" : "FALSE", hwnd
);
1831 return infoPtr
->bUnicode
;
1836 TOOLBAR_HideButton (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1838 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1839 TBUTTON_INFO
*btnPtr
;
1842 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1846 btnPtr
= &infoPtr
->buttons
[nIndex
];
1847 if (LOWORD(lParam
) == FALSE
)
1848 btnPtr
->fsState
&= ~TBSTATE_HIDDEN
;
1850 btnPtr
->fsState
|= TBSTATE_HIDDEN
;
1852 TOOLBAR_CalcToolbar (hwnd
);
1854 InvalidateRect (hwnd
, NULL
, TRUE
);
1860 inline static LRESULT
1861 TOOLBAR_HitTest (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1863 return TOOLBAR_InternalHitTest (hwnd
, (LPPOINT
)lParam
);
1868 TOOLBAR_Indeterminate (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1870 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1871 TBUTTON_INFO
*btnPtr
;
1875 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1879 btnPtr
= &infoPtr
->buttons
[nIndex
];
1880 if (LOWORD(lParam
) == FALSE
)
1881 btnPtr
->fsState
&= ~TBSTATE_INDETERMINATE
;
1883 btnPtr
->fsState
|= TBSTATE_INDETERMINATE
;
1886 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
1887 ReleaseDC (hwnd
, hdc
);
1894 TOOLBAR_InsertButtonA (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1896 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1897 LPTBBUTTON lpTbb
= (LPTBBUTTON
)lParam
;
1898 INT nIndex
= (INT
)wParam
;
1899 TBUTTON_INFO
*oldButtons
;
1905 /* EPP: this seems to be an undocumented call (from my IE4)
1906 * I assume in that case that:
1907 * - lpTbb->iString is a string pointer (not a string index in strings[] table
1908 * - index of insertion is at the end of existing buttons
1909 * I only see this happen with nIndex == -1, but it could have a special
1910 * meaning (like -nIndex (or ~nIndex) to get the real position of insertion).
1912 int len
= lstrlenA((char*)lpTbb
->iString
) + 2;
1913 LPSTR ptr
= COMCTL32_Alloc(len
);
1915 nIndex
= infoPtr
->nNumButtons
;
1916 strcpy(ptr
, (char*)lpTbb
->iString
);
1917 ptr
[len
- 1] = 0; /* ended by two '\0' */
1918 lpTbb
->iString
= TOOLBAR_AddStringA(hwnd
, 0, (LPARAM
)ptr
);
1921 } else if (nIndex
< 0)
1924 TRACE("inserting button index=%d\n", nIndex
);
1925 if (nIndex
> infoPtr
->nNumButtons
) {
1926 nIndex
= infoPtr
->nNumButtons
;
1927 TRACE("adjust index=%d\n", nIndex
);
1930 oldButtons
= infoPtr
->buttons
;
1931 infoPtr
->nNumButtons
++;
1932 infoPtr
->buttons
= COMCTL32_Alloc (sizeof (TBUTTON_INFO
) * infoPtr
->nNumButtons
);
1933 /* pre insert copy */
1935 memcpy (&infoPtr
->buttons
[0], &oldButtons
[0],
1936 nIndex
* sizeof(TBUTTON_INFO
));
1939 /* insert new button */
1940 infoPtr
->buttons
[nIndex
].iBitmap
= lpTbb
->iBitmap
;
1941 infoPtr
->buttons
[nIndex
].idCommand
= lpTbb
->idCommand
;
1942 infoPtr
->buttons
[nIndex
].fsState
= lpTbb
->fsState
;
1943 infoPtr
->buttons
[nIndex
].fsStyle
= lpTbb
->fsStyle
;
1944 infoPtr
->buttons
[nIndex
].dwData
= lpTbb
->dwData
;
1945 infoPtr
->buttons
[nIndex
].iString
= lpTbb
->iString
;
1947 if ((infoPtr
->hwndToolTip
) && !(lpTbb
->fsStyle
& TBSTYLE_SEP
)) {
1950 ZeroMemory (&ti
, sizeof(TTTOOLINFOA
));
1951 ti
.cbSize
= sizeof (TTTOOLINFOA
);
1953 ti
.uId
= lpTbb
->idCommand
;
1955 ti
.lpszText
= LPSTR_TEXTCALLBACKA
;
1957 SendMessageA (infoPtr
->hwndToolTip
, TTM_ADDTOOLA
,
1961 /* post insert copy */
1962 if (nIndex
< infoPtr
->nNumButtons
- 1) {
1963 memcpy (&infoPtr
->buttons
[nIndex
+1], &oldButtons
[nIndex
],
1964 (infoPtr
->nNumButtons
- nIndex
- 1) * sizeof(TBUTTON_INFO
));
1967 COMCTL32_Free (oldButtons
);
1969 TOOLBAR_CalcToolbar (hwnd
);
1971 InvalidateRect (hwnd
, NULL
, FALSE
);
1977 /* << TOOLBAR_InsertButton32W >> */
1978 /* << TOOLBAR_InsertMarkHitTest >> */
1982 TOOLBAR_IsButtonChecked (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1984 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
1987 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
1991 return (infoPtr
->buttons
[nIndex
].fsState
& TBSTATE_CHECKED
);
1996 TOOLBAR_IsButtonEnabled (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
1998 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2001 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
2005 return (infoPtr
->buttons
[nIndex
].fsState
& TBSTATE_ENABLED
);
2010 TOOLBAR_IsButtonHidden (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2012 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2015 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
2019 return (infoPtr
->buttons
[nIndex
].fsState
& TBSTATE_HIDDEN
);
2024 TOOLBAR_IsButtonHighlighted (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2026 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2029 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
2033 return (infoPtr
->buttons
[nIndex
].fsState
& TBSTATE_MARKED
);
2038 TOOLBAR_IsButtonIndeterminate (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2040 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2043 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
2047 return (infoPtr
->buttons
[nIndex
].fsState
& TBSTATE_INDETERMINATE
);
2052 TOOLBAR_IsButtonPressed (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2054 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2057 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
2061 return (infoPtr
->buttons
[nIndex
].fsState
& TBSTATE_PRESSED
);
2065 /* << TOOLBAR_LoadImages >> */
2066 /* << TOOLBAR_MapAccelerator >> */
2067 /* << TOOLBAR_MarkButton >> */
2068 /* << TOOLBAR_MoveButton >> */
2072 TOOLBAR_PressButton (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2074 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2075 TBUTTON_INFO
*btnPtr
;
2079 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
2083 btnPtr
= &infoPtr
->buttons
[nIndex
];
2084 if (LOWORD(lParam
) == FALSE
)
2085 btnPtr
->fsState
&= ~TBSTATE_PRESSED
;
2087 btnPtr
->fsState
|= TBSTATE_PRESSED
;
2090 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
2091 ReleaseDC (hwnd
, hdc
);
2097 /* << TOOLBAR_ReplaceBitmap >> */
2101 TOOLBAR_SaveRestoreA (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2104 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2105 LPTBSAVEPARAMSA lpSave
= (LPTBSAVEPARAMSA
)lParam
;
2107 if (lpSave
== NULL
) return 0;
2110 /* save toolbar information */
2111 FIXME("save to \"%s\" \"%s\"\n",
2112 lpSave
->pszSubKey
, lpSave
->pszValueName
);
2117 /* restore toolbar information */
2119 FIXME("restore from \"%s\" \"%s\"\n",
2120 lpSave
->pszSubKey
, lpSave
->pszValueName
);
2130 /* << TOOLBAR_SaveRestore32W >> */
2131 /* << TOOLBAR_SetAnchorHighlight >> */
2135 TOOLBAR_SetBitmapSize (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2137 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2139 if ((LOWORD(lParam
) <= 0) || (HIWORD(lParam
)<=0))
2142 infoPtr
->nBitmapWidth
= (INT
)LOWORD(lParam
);
2143 infoPtr
->nBitmapHeight
= (INT
)HIWORD(lParam
);
2150 TOOLBAR_SetButtonInfoA (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2152 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2153 LPTBBUTTONINFOA lptbbi
= (LPTBBUTTONINFOA
)lParam
;
2154 TBUTTON_INFO
*btnPtr
;
2159 if (lptbbi
->cbSize
< sizeof(TBBUTTONINFOA
))
2162 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
2166 btnPtr
= &infoPtr
->buttons
[nIndex
];
2167 if (lptbbi
->dwMask
& TBIF_COMMAND
)
2168 btnPtr
->idCommand
= lptbbi
->idCommand
;
2169 if (lptbbi
->dwMask
& TBIF_IMAGE
)
2170 btnPtr
->iBitmap
= lptbbi
->iImage
;
2171 if (lptbbi
->dwMask
& TBIF_LPARAM
)
2172 btnPtr
->dwData
= lptbbi
->lParam
;
2173 /* if (lptbbi->dwMask & TBIF_SIZE) */
2174 /* btnPtr->cx = lptbbi->cx; */
2175 if (lptbbi
->dwMask
& TBIF_STATE
)
2176 btnPtr
->fsState
= lptbbi
->fsState
;
2177 if (lptbbi
->dwMask
& TBIF_STYLE
)
2178 btnPtr
->fsStyle
= lptbbi
->fsStyle
;
2180 if (lptbbi
->dwMask
& TBIF_TEXT
) {
2181 if ((btnPtr
->iString
>= 0) ||
2182 (btnPtr
->iString
< infoPtr
->nNumStrings
)) {
2183 TRACE("Ooooooch\n");
2185 CHAR
**lpString
= &infoPtr
->strings
[btnPtr
->iString
];
2186 INT len
= lstrlenA (lptbbi
->pszText
);
2187 *lpString
= COMCTL32_ReAlloc (lpString
, sizeof(char)*(len
+1));
2190 /* this is the ultimate sollution */
2191 /* Str_SetPtrA (&infoPtr->strings[btnPtr->iString], lptbbi->pszText); */
2199 /* << TOOLBAR_SetButtonInfo32W >> */
2203 TOOLBAR_SetButtonSize (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2205 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2207 if ((LOWORD(lParam
) <= 0) || (HIWORD(lParam
)<=0))
2210 infoPtr
->nButtonWidth
= (INT
)LOWORD(lParam
);
2211 infoPtr
->nButtonHeight
= (INT
)HIWORD(lParam
);
2218 TOOLBAR_SetButtonWidth (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2220 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2222 if (infoPtr
== NULL
)
2225 infoPtr
->cxMin
= (INT
)LOWORD(lParam
);
2226 infoPtr
->cxMax
= (INT
)HIWORD(lParam
);
2233 TOOLBAR_SetCmdId (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2235 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2236 INT nIndex
= (INT
)wParam
;
2238 if ((nIndex
< 0) || (nIndex
>= infoPtr
->nNumButtons
))
2241 infoPtr
->buttons
[nIndex
].idCommand
= (INT
)lParam
;
2243 if (infoPtr
->hwndToolTip
) {
2245 FIXME("change tool tip!\n");
2253 /* << TOOLBAR_SetColorScheme >> */
2257 TOOLBAR_SetDisabledImageList (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2259 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2260 HIMAGELIST himlTemp
;
2262 himlTemp
= infoPtr
->himlDis
;
2263 infoPtr
->himlDis
= (HIMAGELIST
)lParam
;
2265 /* FIXME: redraw ? */
2267 return (LRESULT
)himlTemp
;
2272 TOOLBAR_SetDrawTextFlags (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2274 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2277 dwTemp
= infoPtr
->dwDTFlags
;
2278 infoPtr
->dwDTFlags
=
2279 (infoPtr
->dwDTFlags
& (DWORD
)wParam
) | (DWORD
)lParam
;
2281 return (LRESULT
)dwTemp
;
2286 TOOLBAR_SetExtendedStyle (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2288 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2291 dwTemp
= infoPtr
->dwExStyle
;
2292 infoPtr
->dwExStyle
= (DWORD
)lParam
;
2294 return (LRESULT
)dwTemp
;
2299 TOOLBAR_SetHotImageList (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2301 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr(hwnd
);
2302 HIMAGELIST himlTemp
;
2304 himlTemp
= infoPtr
->himlHot
;
2305 infoPtr
->himlHot
= (HIMAGELIST
)lParam
;
2307 /* FIXME: redraw ? */
2309 return (LRESULT
)himlTemp
;
2313 /* << TOOLBAR_SetHotItem >> */
2317 TOOLBAR_SetImageList (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2319 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2320 HIMAGELIST himlTemp
;
2322 himlTemp
= infoPtr
->himlDef
;
2323 infoPtr
->himlDef
= (HIMAGELIST
)lParam
;
2325 /* FIXME: redraw ? */
2327 return (LRESULT
)himlTemp
;
2332 TOOLBAR_SetIndent (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2334 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2336 infoPtr
->nIndent
= (INT
)wParam
;
2338 TOOLBAR_CalcToolbar (hwnd
);
2340 InvalidateRect(hwnd
, NULL
, FALSE
);
2346 /* << TOOLBAR_SetInsertMark >> */
2350 TOOLBAR_SetInsertMarkColor (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2352 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2354 infoPtr
->clrInsertMark
= (COLORREF
)lParam
;
2356 /* FIXME : redraw ??*/
2363 TOOLBAR_SetMaxTextRows (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2365 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2367 if (infoPtr
== NULL
)
2370 infoPtr
->nMaxTextRows
= (INT
)wParam
;
2376 /* << TOOLBAR_SetPadding >> */
2380 TOOLBAR_SetParent (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2382 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2385 if (infoPtr
== NULL
)
2387 hwndOldNotify
= infoPtr
->hwndNotify
;
2388 infoPtr
->hwndNotify
= (HWND
)wParam
;
2390 return hwndOldNotify
;
2395 TOOLBAR_SetRows (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2397 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2398 LPRECT lprc
= (LPRECT
)lParam
;
2400 if (LOWORD(wParam
) > 1) {
2402 FIXME("multiple rows not supported!\n");
2406 /* recalculate toolbar */
2407 TOOLBAR_CalcToolbar (hwnd
);
2409 /* return bounding rectangle */
2411 lprc
->left
= infoPtr
->rcBound
.left
;
2412 lprc
->right
= infoPtr
->rcBound
.right
;
2413 lprc
->top
= infoPtr
->rcBound
.top
;
2414 lprc
->bottom
= infoPtr
->rcBound
.bottom
;
2417 /* repaint toolbar */
2418 InvalidateRect(hwnd
, NULL
, FALSE
);
2425 TOOLBAR_SetState (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2427 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2428 TBUTTON_INFO
*btnPtr
;
2432 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
2436 btnPtr
= &infoPtr
->buttons
[nIndex
];
2437 btnPtr
->fsState
= LOWORD(lParam
);
2440 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
2441 ReleaseDC (hwnd
, hdc
);
2448 TOOLBAR_SetStyle (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2450 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2451 TBUTTON_INFO
*btnPtr
;
2455 nIndex
= TOOLBAR_GetButtonIndex (infoPtr
, (INT
)wParam
);
2459 btnPtr
= &infoPtr
->buttons
[nIndex
];
2460 btnPtr
->fsStyle
= LOWORD(lParam
);
2463 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
2464 ReleaseDC (hwnd
, hdc
);
2466 if (infoPtr
->hwndToolTip
) {
2468 FIXME("change tool tip!\n");
2476 inline static LRESULT
2477 TOOLBAR_SetToolTips (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2479 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2481 if (infoPtr
== NULL
)
2483 infoPtr
->hwndToolTip
= (HWND
)wParam
;
2489 TOOLBAR_SetUnicodeFormat (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2491 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2494 TRACE("%s hwnd=0x%04x stub!\n",
2495 ((BOOL
)wParam
) ? "TRUE" : "FALSE", hwnd
);
2497 bTemp
= infoPtr
->bUnicode
;
2498 infoPtr
->bUnicode
= (BOOL
)wParam
;
2505 TOOLBAR_Create (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2507 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2508 DWORD dwStyle
= GetWindowLongA (hwnd
, GWL_STYLE
);
2511 /* initialize info structure */
2512 infoPtr
->nButtonHeight
= 22;
2513 infoPtr
->nButtonWidth
= 23;
2514 infoPtr
->nBitmapHeight
= 15;
2515 infoPtr
->nBitmapWidth
= 16;
2517 infoPtr
->nHeight
= infoPtr
->nButtonHeight
+ TOP_BORDER
+ BOTTOM_BORDER
;
2519 infoPtr
->nMaxTextRows
= 1;
2520 infoPtr
->cxMin
= -1;
2521 infoPtr
->cxMax
= -1;
2523 infoPtr
->bCaptured
= FALSE
;
2524 infoPtr
->bUnicode
= IsWindowUnicode (hwnd
);
2525 infoPtr
->nButtonDown
= -1;
2526 infoPtr
->nOldHit
= -1;
2527 infoPtr
->nHotItem
= -2; /* It has to be initially different from nOldHit */
2528 infoPtr
->hwndNotify
= GetParent (hwnd
);
2529 infoPtr
->bTransparent
= (dwStyle
& TBSTYLE_FLAT
);
2530 infoPtr
->dwDTFlags
= DT_CENTER
;
2532 SystemParametersInfoA (SPI_GETICONTITLELOGFONT
, 0, &logFont
, 0);
2533 infoPtr
->hFont
= CreateFontIndirectA (&logFont
);
2535 if (dwStyle
& TBSTYLE_TOOLTIPS
) {
2536 /* Create tooltip control */
2537 infoPtr
->hwndToolTip
=
2538 CreateWindowExA (0, TOOLTIPS_CLASSA
, NULL
, 0,
2539 CW_USEDEFAULT
, CW_USEDEFAULT
,
2540 CW_USEDEFAULT
, CW_USEDEFAULT
,
2543 /* Send NM_TOOLTIPSCREATED notification */
2544 if (infoPtr
->hwndToolTip
) {
2545 NMTOOLTIPSCREATED nmttc
;
2547 nmttc
.hdr
.hwndFrom
= hwnd
;
2548 nmttc
.hdr
.idFrom
= GetWindowLongA (hwnd
, GWL_ID
);
2549 nmttc
.hdr
.code
= NM_TOOLTIPSCREATED
;
2550 nmttc
.hwndToolTips
= infoPtr
->hwndToolTip
;
2552 SendMessageA (infoPtr
->hwndNotify
, WM_NOTIFY
,
2553 (WPARAM
)nmttc
.hdr
.idFrom
, (LPARAM
)&nmttc
);
2562 TOOLBAR_Destroy (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2564 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2566 /* delete tooltip control */
2567 if (infoPtr
->hwndToolTip
)
2568 DestroyWindow (infoPtr
->hwndToolTip
);
2570 /* delete button data */
2571 if (infoPtr
->buttons
)
2572 COMCTL32_Free (infoPtr
->buttons
);
2574 /* delete strings */
2575 if (infoPtr
->strings
) {
2577 for (i
= 0; i
< infoPtr
->nNumStrings
; i
++)
2578 if (infoPtr
->strings
[i
])
2579 COMCTL32_Free (infoPtr
->strings
[i
]);
2581 COMCTL32_Free (infoPtr
->strings
);
2584 /* destroy internal image list */
2585 if (infoPtr
->himlInt
)
2586 ImageList_Destroy (infoPtr
->himlInt
);
2588 /* delete default font */
2590 DeleteObject (infoPtr
->hFont
);
2592 /* free toolbar info data */
2593 COMCTL32_Free (infoPtr
);
2600 TOOLBAR_EraseBackground (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2602 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2604 if (infoPtr
->bTransparent
)
2605 return SendMessageA (GetParent (hwnd
), WM_ERASEBKGND
, wParam
, lParam
);
2607 return DefWindowProcA (hwnd
, WM_ERASEBKGND
, wParam
, lParam
);
2612 TOOLBAR_GetFont (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2614 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2616 return infoPtr
->hFont
;
2621 TOOLBAR_LButtonDblClk (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2623 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2624 TBUTTON_INFO
*btnPtr
;
2629 pt
.x
= (INT
)LOWORD(lParam
);
2630 pt
.y
= (INT
)HIWORD(lParam
);
2631 nHit
= TOOLBAR_InternalHitTest (hwnd
, &pt
);
2634 btnPtr
= &infoPtr
->buttons
[nHit
];
2635 if (!(btnPtr
->fsState
& TBSTATE_ENABLED
))
2638 infoPtr
->bCaptured
= TRUE
;
2639 infoPtr
->nButtonDown
= nHit
;
2641 btnPtr
->fsState
|= TBSTATE_PRESSED
;
2644 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
2645 ReleaseDC (hwnd
, hdc
);
2647 else if (GetWindowLongA (hwnd
, GWL_STYLE
) & CCS_ADJUSTABLE
)
2648 TOOLBAR_Customize (hwnd
);
2655 TOOLBAR_LButtonDown (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2657 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2658 TBUTTON_INFO
*btnPtr
;
2663 if (infoPtr
->hwndToolTip
)
2664 TOOLBAR_RelayEvent (infoPtr
->hwndToolTip
, hwnd
,
2665 WM_LBUTTONDOWN
, wParam
, lParam
);
2667 pt
.x
= (INT
)LOWORD(lParam
);
2668 pt
.y
= (INT
)HIWORD(lParam
);
2669 nHit
= TOOLBAR_InternalHitTest (hwnd
, &pt
);
2672 btnPtr
= &infoPtr
->buttons
[nHit
];
2673 if (!(btnPtr
->fsState
& TBSTATE_ENABLED
))
2677 infoPtr
->bCaptured
= TRUE
;
2678 infoPtr
->nButtonDown
= nHit
;
2679 infoPtr
->nOldHit
= nHit
;
2681 btnPtr
->fsState
|= TBSTATE_PRESSED
;
2684 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
2685 ReleaseDC (hwnd
, hdc
);
2692 TOOLBAR_LButtonUp (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2694 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2695 TBUTTON_INFO
*btnPtr
;
2700 BOOL bSendMessage
= TRUE
;
2702 if (infoPtr
->hwndToolTip
)
2703 TOOLBAR_RelayEvent (infoPtr
->hwndToolTip
, hwnd
,
2704 WM_LBUTTONUP
, wParam
, lParam
);
2706 pt
.x
= (INT
)LOWORD(lParam
);
2707 pt
.y
= (INT
)HIWORD(lParam
);
2708 nHit
= TOOLBAR_InternalHitTest (hwnd
, &pt
);
2710 if ((infoPtr
->bCaptured
) && (infoPtr
->nButtonDown
>= 0)) {
2711 infoPtr
->bCaptured
= FALSE
;
2713 btnPtr
= &infoPtr
->buttons
[infoPtr
->nButtonDown
];
2714 btnPtr
->fsState
&= ~TBSTATE_PRESSED
;
2716 if (nHit
== infoPtr
->nButtonDown
) {
2717 if (btnPtr
->fsStyle
& TBSTYLE_CHECK
) {
2718 if (btnPtr
->fsStyle
& TBSTYLE_GROUP
) {
2719 nOldIndex
= TOOLBAR_GetCheckedGroupButtonIndex (infoPtr
,
2720 infoPtr
->nButtonDown
);
2721 if (nOldIndex
== infoPtr
->nButtonDown
)
2722 bSendMessage
= FALSE
;
2723 if ((nOldIndex
!= infoPtr
->nButtonDown
) &&
2725 infoPtr
->buttons
[nOldIndex
].fsState
&= ~TBSTATE_CHECKED
;
2726 btnPtr
->fsState
|= TBSTATE_CHECKED
;
2729 if (btnPtr
->fsState
& TBSTATE_CHECKED
)
2730 btnPtr
->fsState
&= ~TBSTATE_CHECKED
;
2732 btnPtr
->fsState
|= TBSTATE_CHECKED
;
2737 bSendMessage
= FALSE
;
2740 if (nOldIndex
!= -1)
2741 TOOLBAR_DrawButton (hwnd
, &infoPtr
->buttons
[nOldIndex
], hdc
);
2742 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
2743 ReleaseDC (hwnd
, hdc
);
2746 SendMessageA (GetParent(hwnd
), WM_COMMAND
,
2747 MAKEWPARAM(btnPtr
->idCommand
, 0), (LPARAM
)hwnd
);
2749 if ((GetWindowLongA(hwnd
, GWL_STYLE
) & TBSTYLE_DROPDOWN
) ||
2750 (btnPtr
->fsStyle
& 0x08/* BTNS_DROPDOWN */)) {
2753 nmtb
.hdr
.hwndFrom
= hwnd
;
2754 nmtb
.hdr
.idFrom
= GetWindowLongA (hwnd
, GWL_ID
);
2755 nmtb
.hdr
.code
= TBN_DROPDOWN
;
2757 /* nmtb.tbButton not used with TBN_DROPDOWN */
2758 if ((btnPtr
->iString
>= 0) && (btnPtr
->iString
< infoPtr
->nNumStrings
)) {
2759 nmtb
.pszText
= infoPtr
->strings
[btnPtr
->iString
];
2760 nmtb
.cchText
= lstrlenW(nmtb
.pszText
);
2762 nmtb
.pszText
= NULL
;
2765 nmtb
.rcButton
= btnPtr
->rect
;
2767 SendMessageW(infoPtr
->hwndNotify
, WM_NOTIFY
,
2768 (WPARAM
)nmtb
.hdr
.idFrom
, (LPARAM
)&nmtb
);
2771 infoPtr
->nButtonDown
= -1;
2772 infoPtr
->nOldHit
= -1;
2780 TOOLBAR_MouseMove (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2782 TBUTTON_INFO
*btnPtr
, *oldBtnPtr
;
2783 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2788 if (infoPtr
->hwndToolTip
)
2789 TOOLBAR_RelayEvent (infoPtr
->hwndToolTip
, hwnd
,
2790 WM_MOUSEMOVE
, wParam
, lParam
);
2792 pt
.x
= (INT
)LOWORD(lParam
);
2793 pt
.y
= (INT
)HIWORD(lParam
);
2795 nHit
= TOOLBAR_InternalHitTest (hwnd
, &pt
);
2797 if (infoPtr
->nOldHit
!= nHit
)
2799 /* Remove the effect of an old hot button */
2800 if(infoPtr
->nOldHit
== infoPtr
->nHotItem
)
2802 oldBtnPtr
= &infoPtr
->buttons
[infoPtr
->nOldHit
];
2803 oldBtnPtr
->bHot
= FALSE
;
2805 InvalidateRect (hwnd
, &oldBtnPtr
->rect
, TRUE
);
2808 /* It's not a separator or in nowhere. It's a hot button. */
2811 btnPtr
= &infoPtr
->buttons
[nHit
];
2812 btnPtr
->bHot
= TRUE
;
2815 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
2816 ReleaseDC (hwnd
, hdc
);
2818 infoPtr
->nHotItem
= nHit
;
2821 if (infoPtr
->bCaptured
) {
2822 btnPtr
= &infoPtr
->buttons
[infoPtr
->nButtonDown
];
2823 if (infoPtr
->nOldHit
== infoPtr
->nButtonDown
) {
2824 btnPtr
->fsState
&= ~TBSTATE_PRESSED
;
2826 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
2827 ReleaseDC (hwnd
, hdc
);
2829 else if (nHit
== infoPtr
->nButtonDown
) {
2830 btnPtr
->fsState
|= TBSTATE_PRESSED
;
2832 TOOLBAR_DrawButton (hwnd
, btnPtr
, hdc
);
2833 ReleaseDC (hwnd
, hdc
);
2836 infoPtr
->nOldHit
= nHit
;
2842 inline static LRESULT
2843 TOOLBAR_NCActivate (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2845 /* if (wndPtr->dwStyle & CCS_NODIVIDER) */
2846 return DefWindowProcA (hwnd
, WM_NCACTIVATE
, wParam
, lParam
);
2848 /* return TOOLBAR_NCPaint (wndPtr, wParam, lParam); */
2852 inline static LRESULT
2853 TOOLBAR_NCCalcSize (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2855 if (!(GetWindowLongA (hwnd
, GWL_STYLE
) & CCS_NODIVIDER
))
2856 ((LPRECT
)lParam
)->top
+= GetSystemMetrics(SM_CYEDGE
);
2858 return DefWindowProcA (hwnd
, WM_NCCALCSIZE
, wParam
, lParam
);
2863 TOOLBAR_NCCreate (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2865 TOOLBAR_INFO
*infoPtr
;
2867 /* allocate memory for info structure */
2868 infoPtr
= (TOOLBAR_INFO
*)COMCTL32_Alloc (sizeof(TOOLBAR_INFO
));
2869 SetWindowLongA (hwnd
, 0, (DWORD
)infoPtr
);
2872 infoPtr
->dwStructSize
= sizeof(TBBUTTON
);
2874 /* fix instance handle, if the toolbar was created by CreateToolbarEx() */
2875 if (!GetWindowLongA (hwnd
, GWL_HINSTANCE
)) {
2876 HINSTANCE hInst
= (HINSTANCE
)GetWindowLongA (GetParent (hwnd
), GWL_HINSTANCE
);
2877 SetWindowLongA (hwnd
, GWL_HINSTANCE
, (DWORD
)hInst
);
2880 return DefWindowProcA (hwnd
, WM_NCCREATE
, wParam
, lParam
);
2885 TOOLBAR_NCPaint (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2887 DWORD dwStyle
= GetWindowLongA (hwnd
, GWL_STYLE
);
2891 if (dwStyle
& WS_MINIMIZE
)
2892 return 0; /* Nothing to do */
2894 DefWindowProcA (hwnd
, WM_NCPAINT
, wParam
, lParam
);
2896 if (!(hdc
= GetDCEx (hwnd
, 0, DCX_USESTYLE
| DCX_WINDOW
)))
2899 if (!(dwStyle
& CCS_NODIVIDER
))
2901 GetWindowRect (hwnd
, &rcWindow
);
2902 OffsetRect (&rcWindow
, -rcWindow
.left
, -rcWindow
.top
);
2903 DrawEdge (hdc
, &rcWindow
, EDGE_ETCHED
, BF_TOP
);
2906 ReleaseDC( hwnd
, hdc
);
2912 inline static LRESULT
2913 TOOLBAR_Notify (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2915 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2916 LPNMHDR lpnmh
= (LPNMHDR
)lParam
;
2918 TRACE("passing WM_NOTIFY!\n");
2920 if ((infoPtr
->hwndToolTip
) && (lpnmh
->hwndFrom
== infoPtr
->hwndToolTip
)) {
2921 SendMessageA (infoPtr
->hwndNotify
, WM_NOTIFY
, wParam
, lParam
);
2924 if (lpnmh
->code
== TTN_GETDISPINFOA
) {
2925 LPNMTTDISPINFOA lpdi
= (LPNMTTDISPINFOA
)lParam
;
2927 FIXME("retrieving ASCII string\n");
2930 else if (lpnmh
->code
== TTN_GETDISPINFOW
) {
2931 LPNMTTDISPINFOW lpdi
= (LPNMTTDISPINFOW
)lParam
;
2933 FIXME("retrieving UNICODE string\n");
2944 TOOLBAR_Paint (HWND hwnd
, WPARAM wParam
)
2949 TOOLBAR_CalcToolbar( hwnd
);
2950 hdc
= wParam
==0 ? BeginPaint (hwnd
, &ps
) : (HDC
)wParam
;
2951 TOOLBAR_Refresh (hwnd
, hdc
);
2953 EndPaint (hwnd
, &ps
);
2959 TOOLBAR_Size (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
2961 TOOLBAR_INFO
*infoPtr
= TOOLBAR_GetInfoPtr (hwnd
);
2962 DWORD dwStyle
= GetWindowLongA (hwnd
, GWL_STYLE
);
2970 /* Resize deadlock check */
2971 if (infoPtr
->bAutoSize
) {
2972 infoPtr
->bAutoSize
= FALSE
;
2976 flags
= (INT
) wParam
;
2978 /* FIXME for flags =
2979 * SIZE_MAXIMIZED, SIZE_MAXSHOW, SIZE_MINIMIZED
2982 TRACE("sizing toolbar!\n");
2984 if (flags
== SIZE_RESTORED
) {
2985 /* width and height don't apply */
2986 parent
= GetParent (hwnd
);
2987 GetClientRect(parent
, &parent_rect
);
2989 if (dwStyle
& CCS_NORESIZE
) {
2990 uPosFlags
|= (SWP_NOSIZE
| SWP_NOMOVE
);
2993 /* infoPtr->nWidth = parent_rect.right - parent_rect.left; */
2994 cy
= infoPtr
->nHeight
;
2995 cx
= infoPtr
->nWidth
;
2996 TOOLBAR_CalcToolbar (hwnd
);
2997 infoPtr
->nWidth
= cx
;
2998 infoPtr
->nHeight
= cy
;
3001 infoPtr
->nWidth
= parent_rect
.right
- parent_rect
.left
;
3002 TOOLBAR_CalcToolbar (hwnd
);
3003 cy
= infoPtr
->nHeight
;
3004 cx
= infoPtr
->nWidth
;
3007 if (dwStyle
& CCS_NOPARENTALIGN
) {
3008 uPosFlags
|= SWP_NOMOVE
;
3009 cy
= infoPtr
->nHeight
;
3010 cx
= infoPtr
->nWidth
;
3013 if (!(dwStyle
& CCS_NODIVIDER
))
3014 cy
+= GetSystemMetrics(SM_CYEDGE
);
3016 SetWindowPos (hwnd
, 0, parent_rect
.left
, parent_rect
.top
,
3017 cx
, cy
, uPosFlags
| SWP_NOZORDER
);
3024 TOOLBAR_StyleChanged (HWND hwnd
, WPARAM wParam
, LPARAM lParam
)
3026 TOOLBAR_AutoSize (hwnd
, wParam
, lParam
);
3028 InvalidateRect(hwnd
, NULL
, FALSE
);
3035 static LRESULT WINAPI
3036 ToolbarWindowProc (HWND hwnd
, UINT uMsg
, WPARAM wParam
, LPARAM lParam
)
3041 return TOOLBAR_AddBitmap (hwnd
, wParam
, lParam
);
3043 case TB_ADDBUTTONSA
:
3044 return TOOLBAR_AddButtonsA (hwnd
, wParam
, lParam
);
3046 /* case TB_ADDBUTTONSW: */
3049 return TOOLBAR_AddStringA (hwnd
, wParam
, lParam
);
3052 return TOOLBAR_AddStringW (hwnd
, wParam
, lParam
);
3055 return TOOLBAR_AutoSize (hwnd
, wParam
, lParam
);
3057 case TB_BUTTONCOUNT
:
3058 return TOOLBAR_ButtonCount (hwnd
, wParam
, lParam
);
3060 case TB_BUTTONSTRUCTSIZE
:
3061 return TOOLBAR_ButtonStructSize (hwnd
, wParam
, lParam
);
3063 case TB_CHANGEBITMAP
:
3064 return TOOLBAR_ChangeBitmap (hwnd
, wParam
, lParam
);
3066 case TB_CHECKBUTTON
:
3067 return TOOLBAR_CheckButton (hwnd
, wParam
, lParam
);
3069 case TB_COMMANDTOINDEX
:
3070 return TOOLBAR_CommandToIndex (hwnd
, wParam
, lParam
);
3073 return TOOLBAR_Customize (hwnd
);
3075 case TB_DELETEBUTTON
:
3076 return TOOLBAR_DeleteButton (hwnd
, wParam
, lParam
);
3078 case TB_ENABLEBUTTON
:
3079 return TOOLBAR_EnableButton (hwnd
, wParam
, lParam
);
3081 /* case TB_GETANCHORHIGHLIGHT: */ /* 4.71 */
3084 return TOOLBAR_GetBitmap (hwnd
, wParam
, lParam
);
3086 case TB_GETBITMAPFLAGS
:
3087 return TOOLBAR_GetBitmapFlags (hwnd
, wParam
, lParam
);
3090 return TOOLBAR_GetButton (hwnd
, wParam
, lParam
);
3092 case TB_GETBUTTONINFOA
:
3093 return TOOLBAR_GetButtonInfoA (hwnd
, wParam
, lParam
);
3095 /* case TB_GETBUTTONINFOW: */ /* 4.71 */
3097 case TB_GETBUTTONSIZE
:
3098 return TOOLBAR_GetButtonSize (hwnd
);
3100 case TB_GETBUTTONTEXTA
:
3101 return TOOLBAR_GetButtonTextA (hwnd
, wParam
, lParam
);
3103 /* case TB_GETBUTTONTEXTW: */
3104 /* case TB_GETCOLORSCHEME: */ /* 4.71 */
3106 case TB_GETDISABLEDIMAGELIST
:
3107 return TOOLBAR_GetDisabledImageList (hwnd
, wParam
, lParam
);
3109 case TB_GETEXTENDEDSTYLE
:
3110 return TOOLBAR_GetExtendedStyle (hwnd
);
3112 case TB_GETHOTIMAGELIST
:
3113 return TOOLBAR_GetHotImageList (hwnd
, wParam
, lParam
);
3115 /* case TB_GETHOTITEM: */ /* 4.71 */
3117 case TB_GETIMAGELIST
:
3118 return TOOLBAR_GetImageList (hwnd
, wParam
, lParam
);
3120 /* case TB_GETINSERTMARK: */ /* 4.71 */
3121 /* case TB_GETINSERTMARKCOLOR: */ /* 4.71 */
3123 case TB_GETITEMRECT
:
3124 return TOOLBAR_GetItemRect (hwnd
, wParam
, lParam
);
3127 return TOOLBAR_GetMaxSize (hwnd
, wParam
, lParam
);
3129 /* case TB_GETOBJECT: */ /* 4.71 */
3130 /* case TB_GETPADDING: */ /* 4.71 */
3133 return TOOLBAR_GetRect (hwnd
, wParam
, lParam
);
3136 return TOOLBAR_GetRows (hwnd
, wParam
, lParam
);
3139 return TOOLBAR_GetState (hwnd
, wParam
, lParam
);
3142 return TOOLBAR_GetStyle (hwnd
, wParam
, lParam
);
3144 case TB_GETTEXTROWS
:
3145 return TOOLBAR_GetTextRows (hwnd
, wParam
, lParam
);
3147 case TB_GETTOOLTIPS
:
3148 return TOOLBAR_GetToolTips (hwnd
, wParam
, lParam
);
3150 case TB_GETUNICODEFORMAT
:
3151 return TOOLBAR_GetUnicodeFormat (hwnd
, wParam
, lParam
);
3154 return TOOLBAR_HideButton (hwnd
, wParam
, lParam
);
3157 return TOOLBAR_HitTest (hwnd
, wParam
, lParam
);
3159 case TB_INDETERMINATE
:
3160 return TOOLBAR_Indeterminate (hwnd
, wParam
, lParam
);
3162 case TB_INSERTBUTTONA
:
3163 return TOOLBAR_InsertButtonA (hwnd
, wParam
, lParam
);
3165 /* case TB_INSERTBUTTONW: */
3166 /* case TB_INSERTMARKHITTEST: */ /* 4.71 */
3168 case TB_ISBUTTONCHECKED
:
3169 return TOOLBAR_IsButtonChecked (hwnd
, wParam
, lParam
);
3171 case TB_ISBUTTONENABLED
:
3172 return TOOLBAR_IsButtonEnabled (hwnd
, wParam
, lParam
);
3174 case TB_ISBUTTONHIDDEN
:
3175 return TOOLBAR_IsButtonHidden (hwnd
, wParam
, lParam
);
3177 case TB_ISBUTTONHIGHLIGHTED
:
3178 return TOOLBAR_IsButtonHighlighted (hwnd
, wParam
, lParam
);
3180 case TB_ISBUTTONINDETERMINATE
:
3181 return TOOLBAR_IsButtonIndeterminate (hwnd
, wParam
, lParam
);
3183 case TB_ISBUTTONPRESSED
:
3184 return TOOLBAR_IsButtonPressed (hwnd
, wParam
, lParam
);
3186 case TB_LOADIMAGES
: /* 4.70 */
3187 FIXME("missing standard imagelists\n");
3190 /* case TB_MAPACCELERATORA: */ /* 4.71 */
3191 /* case TB_MAPACCELERATORW: */ /* 4.71 */
3192 /* case TB_MARKBUTTON: */ /* 4.71 */
3193 /* case TB_MOVEBUTTON: */ /* 4.71 */
3195 case TB_PRESSBUTTON
:
3196 return TOOLBAR_PressButton (hwnd
, wParam
, lParam
);
3198 /* case TB_REPLACEBITMAP: */
3200 case TB_SAVERESTOREA
:
3201 return TOOLBAR_SaveRestoreA (hwnd
, wParam
, lParam
);
3203 /* case TB_SAVERESTOREW: */
3204 /* case TB_SETANCHORHIGHLIGHT: */ /* 4.71 */
3206 case TB_SETBITMAPSIZE
:
3207 return TOOLBAR_SetBitmapSize (hwnd
, wParam
, lParam
);
3209 case TB_SETBUTTONINFOA
:
3210 return TOOLBAR_SetButtonInfoA (hwnd
, wParam
, lParam
);
3212 /* case TB_SETBUTTONINFOW: */ /* 4.71 */
3214 case TB_SETBUTTONSIZE
:
3215 return TOOLBAR_SetButtonSize (hwnd
, wParam
, lParam
);
3217 case TB_SETBUTTONWIDTH
:
3218 return TOOLBAR_SetButtonWidth (hwnd
, wParam
, lParam
);
3221 return TOOLBAR_SetCmdId (hwnd
, wParam
, lParam
);
3223 /* case TB_SETCOLORSCHEME: */ /* 4.71 */
3225 case TB_SETDISABLEDIMAGELIST
:
3226 return TOOLBAR_SetDisabledImageList (hwnd
, wParam
, lParam
);
3228 case TB_SETDRAWTEXTFLAGS
:
3229 return TOOLBAR_SetDrawTextFlags (hwnd
, wParam
, lParam
);
3231 case TB_SETEXTENDEDSTYLE
:
3232 return TOOLBAR_SetExtendedStyle (hwnd
, wParam
, lParam
);
3234 case TB_SETHOTIMAGELIST
:
3235 return TOOLBAR_SetHotImageList (hwnd
, wParam
, lParam
);
3237 /* case TB_SETHOTITEM: */ /* 4.71 */
3239 case TB_SETIMAGELIST
:
3240 return TOOLBAR_SetImageList (hwnd
, wParam
, lParam
);
3243 return TOOLBAR_SetIndent (hwnd
, wParam
, lParam
);
3245 /* case TB_SETINSERTMARK: */ /* 4.71 */
3247 case TB_SETINSERTMARKCOLOR
:
3248 return TOOLBAR_SetInsertMarkColor (hwnd
, wParam
, lParam
);
3250 case TB_SETMAXTEXTROWS
:
3251 return TOOLBAR_SetMaxTextRows (hwnd
, wParam
, lParam
);
3253 /* case TB_SETPADDING: */ /* 4.71 */
3256 return TOOLBAR_SetParent (hwnd
, wParam
, lParam
);
3259 return TOOLBAR_SetRows (hwnd
, wParam
, lParam
);
3262 return TOOLBAR_SetState (hwnd
, wParam
, lParam
);
3265 return TOOLBAR_SetStyle (hwnd
, wParam
, lParam
);
3267 case TB_SETTOOLTIPS
:
3268 return TOOLBAR_SetToolTips (hwnd
, wParam
, lParam
);
3270 case TB_SETUNICODEFORMAT
:
3271 return TOOLBAR_SetUnicodeFormat (hwnd
, wParam
, lParam
);
3277 return TOOLBAR_Create (hwnd
, wParam
, lParam
);
3280 return TOOLBAR_Destroy (hwnd
, wParam
, lParam
);
3283 return TOOLBAR_EraseBackground (hwnd
, wParam
, lParam
);
3286 return TOOLBAR_GetFont (hwnd
, wParam
, lParam
);
3288 /* case WM_KEYDOWN: */
3289 /* case WM_KILLFOCUS: */
3291 case WM_LBUTTONDBLCLK
:
3292 return TOOLBAR_LButtonDblClk (hwnd
, wParam
, lParam
);
3294 case WM_LBUTTONDOWN
:
3295 return TOOLBAR_LButtonDown (hwnd
, wParam
, lParam
);
3298 return TOOLBAR_LButtonUp (hwnd
, wParam
, lParam
);
3301 return TOOLBAR_MouseMove (hwnd
, wParam
, lParam
);
3304 return TOOLBAR_NCActivate (hwnd
, wParam
, lParam
);
3307 return TOOLBAR_NCCalcSize (hwnd
, wParam
, lParam
);
3310 return TOOLBAR_NCCreate (hwnd
, wParam
, lParam
);
3313 return TOOLBAR_NCPaint (hwnd
, wParam
, lParam
);
3316 return TOOLBAR_Notify (hwnd
, wParam
, lParam
);
3318 /* case WM_NOTIFYFORMAT: */
3321 return TOOLBAR_Paint (hwnd
, wParam
);
3324 return TOOLBAR_Size (hwnd
, wParam
, lParam
);
3326 case WM_STYLECHANGED
:
3327 return TOOLBAR_StyleChanged (hwnd
, wParam
, lParam
);
3329 /* case WM_SYSCOLORCHANGE: */
3331 /* case WM_WININICHANGE: */
3336 case WM_MEASUREITEM
:
3338 return SendMessageA (GetParent (hwnd
), uMsg
, wParam
, lParam
);
3341 if (uMsg
>= WM_USER
)
3342 ERR("unknown msg %04x wp=%08x lp=%08lx\n",
3343 uMsg
, wParam
, lParam
);
3344 return DefWindowProcA (hwnd
, uMsg
, wParam
, lParam
);
3351 TOOLBAR_Register (void)
3355 if (GlobalFindAtomA (TOOLBARCLASSNAMEA
)) return;
3357 ZeroMemory (&wndClass
, sizeof(WNDCLASSA
));
3358 wndClass
.style
= CS_GLOBALCLASS
| CS_DBLCLKS
;
3359 wndClass
.lpfnWndProc
= (WNDPROC
)ToolbarWindowProc
;
3360 wndClass
.cbClsExtra
= 0;
3361 wndClass
.cbWndExtra
= sizeof(TOOLBAR_INFO
*);
3362 wndClass
.hCursor
= LoadCursorA (0, IDC_ARROWA
);
3363 wndClass
.hbrBackground
= (HBRUSH
)(COLOR_3DFACE
+ 1);
3364 wndClass
.lpszClassName
= TOOLBARCLASSNAMEA
;
3366 RegisterClassA (&wndClass
);
3371 TOOLBAR_Unregister (void)
3373 if (GlobalFindAtomA (TOOLBARCLASSNAMEA
))
3374 UnregisterClassA (TOOLBARCLASSNAMEA
, (HINSTANCE
)NULL
);