2 * Non-client area window functions
4 * Copyright 1994 Alexandre Julliard
11 #include "sysmetrics.h"
14 #include "cursoricon.h"
20 #include "nonclient.h"
22 #include "selectors.h"
28 static HBITMAP16 hbitmapClose
= 0;
29 static HBITMAP16 hbitmapCloseD
= 0;
30 static HBITMAP16 hbitmapMinimize
= 0;
31 static HBITMAP16 hbitmapMinimizeD
= 0;
32 static HBITMAP16 hbitmapMaximize
= 0;
33 static HBITMAP16 hbitmapMaximizeD
= 0;
34 static HBITMAP16 hbitmapRestore
= 0;
35 static HBITMAP16 hbitmapRestoreD
= 0;
37 #define SC_ABOUTWINE (SC_SCREENSAVE+1)
38 #define SC_PUTMARK (SC_SCREENSAVE+2)
40 /* Some useful macros */
41 #define HAS_DLGFRAME(style,exStyle) \
42 (((exStyle) & WS_EX_DLGMODALFRAME) || \
43 (((style) & WS_DLGFRAME) && !((style) & WS_BORDER)))
45 #define HAS_THICKFRAME(style) \
46 (((style) & WS_THICKFRAME) && \
47 !(((style) & (WS_DLGFRAME|WS_BORDER)) == WS_DLGFRAME))
49 #define HAS_FIXEDFRAME(style,exStyle) \
50 (((((exStyle) & WS_EX_DLGMODALFRAME) || \
51 ((style) & WS_DLGFRAME)) && ((style) & WS_BORDER)) && \
52 !((style) & WS_THICKFRAME))
54 #define HAS_SIZEFRAME(style) \
55 (((style) & WS_THICKFRAME) && \
56 !(((style) & (WS_DLGFRAME|WS_BORDER)) == WS_DLGFRAME))
58 #define HAS_MENU(w) (!((w)->dwStyle & WS_CHILD) && ((w)->wIDmenu != 0))
60 #define ON_LEFT_BORDER(hit) \
61 (((hit) == HTLEFT) || ((hit) == HTTOPLEFT) || ((hit) == HTBOTTOMLEFT))
62 #define ON_RIGHT_BORDER(hit) \
63 (((hit) == HTRIGHT) || ((hit) == HTTOPRIGHT) || ((hit) == HTBOTTOMRIGHT))
64 #define ON_TOP_BORDER(hit) \
65 (((hit) == HTTOP) || ((hit) == HTTOPLEFT) || ((hit) == HTTOPRIGHT))
66 #define ON_BOTTOM_BORDER(hit) \
67 (((hit) == HTBOTTOM) || ((hit) == HTBOTTOMLEFT) || ((hit) == HTBOTTOMRIGHT))
69 /***********************************************************************
72 * Compute the size of the window rectangle from the size of the
75 static void NC_AdjustRect( LPRECT16 rect
, DWORD style
, BOOL32 menu
,
78 if (TWEAK_WineLook
> WIN31_LOOK
)
79 ERR(nonclient
, "Called in Win95 mode. Aiee! Please report this.\n" );
81 if(style
& WS_ICONIC
) return;
82 /* Decide if the window will be managed (see CreateWindowEx) */
83 if (!(Options
.managed
&& !(style
& WS_CHILD
) &&
84 ((style
& (WS_DLGFRAME
| WS_THICKFRAME
)) ||
85 (exStyle
& WS_EX_DLGMODALFRAME
))))
87 if (HAS_DLGFRAME( style
, exStyle
))
88 InflateRect16(rect
, SYSMETRICS_CXDLGFRAME
, SYSMETRICS_CYDLGFRAME
);
91 if (HAS_THICKFRAME(style
))
92 InflateRect16( rect
, SYSMETRICS_CXFRAME
, SYSMETRICS_CYFRAME
);
93 if (style
& WS_BORDER
)
94 InflateRect16( rect
, SYSMETRICS_CXBORDER
, SYSMETRICS_CYBORDER
);
97 if ((style
& WS_CAPTION
) == WS_CAPTION
)
98 rect
->top
-= SYSMETRICS_CYCAPTION
- SYSMETRICS_CYBORDER
;
100 if (menu
) rect
->top
-= SYSMETRICS_CYMENU
+ SYSMETRICS_CYBORDER
;
102 if (style
& WS_VSCROLL
) {
103 rect
->right
+= SYSMETRICS_CXVSCROLL
- 1;
104 if(!(style
& WS_BORDER
))
108 if (style
& WS_HSCROLL
) {
109 rect
->bottom
+= SYSMETRICS_CYHSCROLL
- 1;
110 if(!(style
& WS_BORDER
))
116 /******************************************************************************
117 * NC_AdjustRectOuter95
119 * Computes the size of the "outside" parts of the window based on the
120 * parameters of the client area.
129 * "Outer" parts of a window means the whole window frame, caption and
130 * menu bar. It does not include "inner" parts of the frame like client
131 * edge, static edge or scroll bars.
134 * 05-Jul-1997 Dave Cuthbert (dacut@ece.cmu.edu)
135 * Original (NC_AdjustRect95) cut & paste from NC_AdjustRect
137 * 20-Jun-1998 Eric Kohl (ekohl@abo.rhein-zeitung.de)
138 * Split NC_AdjustRect95 into NC_AdjustRectOuter95 and
139 * NC_AdjustRectInner95 and added handling of Win95 styles.
141 *****************************************************************************/
144 NC_AdjustRectOuter95 (LPRECT16 rect
, DWORD style
, BOOL32 menu
, DWORD exStyle
)
146 if(style
& WS_ICONIC
) return;
148 /* Decide if the window will be managed (see CreateWindowEx) */
149 if (!(Options
.managed
&& !(style
& WS_CHILD
) &&
150 ((style
& (WS_DLGFRAME
| WS_THICKFRAME
)) ||
151 (exStyle
& WS_EX_DLGMODALFRAME
))))
153 if (HAS_FIXEDFRAME( style
, exStyle
))
154 InflateRect16(rect
, SYSMETRICS_CXDLGFRAME
, SYSMETRICS_CYDLGFRAME
);
157 if (HAS_SIZEFRAME(style
))
158 InflateRect16( rect
, SYSMETRICS_CXFRAME
, SYSMETRICS_CYFRAME
);
160 if (style
& WS_BORDER
)
161 InflateRect16( rect
, SYSMETRICS_CXBORDER
, SYSMETRICS_CYBORDER
);
165 if ((style
& WS_CAPTION
) == WS_CAPTION
)
167 if (exStyle
& WS_EX_TOOLWINDOW
)
168 rect
->top
-= SYSMETRICS_CYSMCAPTION
;
170 rect
->top
-= SYSMETRICS_CYCAPTION
;
175 rect
->top
-= sysMetrics
[SM_CYMENU
];
179 /******************************************************************************
180 * NC_AdjustRectInner95
182 * Computes the size of the "inside" part of the window based on the
183 * parameters of the client area.
191 * "Inner" part of a window means the window frame inside of the flat
192 * window frame. It includes the client edge, the static edge and the
196 * 05-Jul-1997 Dave Cuthbert (dacut@ece.cmu.edu)
197 * Original (NC_AdjustRect95) cut & paste from NC_AdjustRect
199 * 20-Jun-1998 Eric Kohl (ekohl@abo.rhein-zeitung.de)
200 * Split NC_AdjustRect95 into NC_AdjustRectOuter95 and
201 * NC_AdjustRectInner95 and added handling of Win95 styles.
203 *****************************************************************************/
206 NC_AdjustRectInner95 (LPRECT16 rect
, DWORD style
, DWORD exStyle
)
208 if(style
& WS_ICONIC
) return;
210 if (exStyle
& WS_EX_CLIENTEDGE
)
211 InflateRect16 (rect
, sysMetrics
[SM_CXEDGE
], sysMetrics
[SM_CYEDGE
]);
213 if (exStyle
& WS_EX_STATICEDGE
)
214 InflateRect16 (rect
, sysMetrics
[SM_CXBORDER
], sysMetrics
[SM_CYBORDER
]);
216 if (style
& WS_VSCROLL
) rect
->right
+= SYSMETRICS_CXVSCROLL
;
217 if (style
& WS_HSCROLL
) rect
->bottom
+= SYSMETRICS_CYHSCROLL
;
221 /***********************************************************************
222 * DrawCaption16 [USER.660] Draws a caption bar
236 DrawCaption16 (HWND16 hwnd
, HDC16 hdc
, const RECT16
*rect
, UINT16 uFlags
)
241 CONV_RECT16TO32 (rect
, &rect32
);
243 return (BOOL16
)DrawCaptionTemp32A (hwnd
, hdc
, rect
? &rect32
: NULL
,
244 0, 0, NULL
, uFlags
& 0x1F);
248 /***********************************************************************
249 * DrawCaption32 [USER32.154] Draws a caption bar
263 DrawCaption32 (HWND32 hwnd
, HDC32 hdc
, const RECT32
*lpRect
, UINT32 uFlags
)
265 return DrawCaptionTemp32A (hwnd
, hdc
, lpRect
, 0, 0, NULL
, uFlags
& 0x1F);
269 /***********************************************************************
270 * DrawCaptionTemp16 [USER.657]
280 DrawCaptionTemp16 (HWND16 hwnd
, HDC16 hdc
, const RECT16
*rect
, HFONT16 hFont
,
281 HICON16 hIcon
, LPCSTR str
, UINT16 uFlags
)
286 CONV_RECT16TO32(rect
,&rect32
);
288 return (BOOL16
)DrawCaptionTemp32A (hwnd
, hdc
, rect
?&rect32
:NULL
, hFont
,
289 hIcon
, str
, uFlags
& 0x1F);
293 /***********************************************************************
294 * DrawCaptionTemp32A [USER32.599]
304 DrawCaptionTemp32A (HWND32 hwnd
, HDC32 hdc
, const RECT32
*rect
, HFONT32 hFont
,
305 HICON32 hIcon
, LPCSTR str
, UINT32 uFlags
)
309 TRACE (nonclient
, "(%08x,%08x,%p,%08x,%08x,\"%s\",%08x)\n",
310 hwnd
, hdc
, rect
, hFont
, hIcon
, str
, uFlags
);
312 /* drawing background */
313 if (uFlags
& DC_INBUTTON
) {
314 FillRect32 (hdc
, &rc
, GetSysColorBrush32 (COLOR_3DFACE
));
316 if (uFlags
& DC_ACTIVE
) {
317 HBRUSH32 hbr
= SelectObject32 (hdc
, CACHE_GetPattern55AABrush ());
318 PatBlt32 (hdc
, rc
.left
, rc
.top
,
319 rc
.right
-rc
.left
, rc
.bottom
-rc
.top
, 0xFA0089);
320 SelectObject32 (hdc
, hbr
);
324 FillRect32 (hdc
, &rc
, GetSysColorBrush32 ((uFlags
& DC_ACTIVE
) ?
325 COLOR_ACTIVECAPTION
: COLOR_INACTIVECAPTION
));
330 if ((uFlags
& DC_ICON
) && !(uFlags
& DC_SMALLCAP
)) {
334 pt
.y
= (rc
.bottom
+ rc
.top
- sysMetrics
[SM_CYSMICON
]) / 2;
337 DrawIconEx32 (hdc
, pt
.x
, pt
.y
, hIcon
, sysMetrics
[SM_CXSMICON
],
338 sysMetrics
[SM_CYSMICON
], 0, 0, DI_NORMAL
);
341 WND
*wndPtr
= WIN_FindWndPtr(hwnd
);
342 HICON32 hAppIcon
= 0;
344 if (wndPtr
->class->hIconSm
)
345 hAppIcon
= wndPtr
->class->hIconSm
;
346 else if (wndPtr
->class->hIcon
)
347 hAppIcon
= wndPtr
->class->hIcon
;
349 DrawIconEx32 (hdc
, pt
.x
, pt
.y
, hAppIcon
, sysMetrics
[SM_CXSMICON
],
350 sysMetrics
[SM_CYSMICON
], 0, 0, DI_NORMAL
);
353 rc
.left
+= (rc
.bottom
- rc
.top
);
357 if (uFlags
& DC_TEXT
) {
360 if (uFlags
& DC_INBUTTON
)
361 SetTextColor32 (hdc
, GetSysColor32 (COLOR_BTNTEXT
));
362 else if (uFlags
& DC_ACTIVE
)
363 SetTextColor32 (hdc
, GetSysColor32 (COLOR_CAPTIONTEXT
));
365 SetTextColor32 (hdc
, GetSysColor32 (COLOR_INACTIVECAPTIONTEXT
));
367 SetBkMode32 (hdc
, TRANSPARENT
);
370 hOldFont
= SelectObject32 (hdc
, hFont
);
372 NONCLIENTMETRICS32A nclm
;
374 nclm
.cbSize
= sizeof(NONCLIENTMETRICS32A
);
375 SystemParametersInfo32A (SPI_GETNONCLIENTMETRICS
, 0, &nclm
, 0);
376 hNewFont
= CreateFontIndirect32A ((uFlags
& DC_SMALLCAP
) ?
377 &nclm
.lfSmCaptionFont
: &nclm
.lfCaptionFont
);
378 hOldFont
= SelectObject32 (hdc
, hNewFont
);
382 DrawText32A (hdc
, str
, -1, &rc
,
383 DT_SINGLELINE
| DT_VCENTER
| DT_NOPREFIX
| DT_LEFT
);
387 nLen
= GetWindowText32A (hwnd
, szText
, 128);
388 DrawText32A (hdc
, szText
, nLen
, &rc
,
389 DT_SINGLELINE
| DT_VCENTER
| DT_NOPREFIX
| DT_LEFT
);
393 SelectObject32 (hdc
, hOldFont
);
395 DeleteObject32 (SelectObject32 (hdc
, hOldFont
));
398 /* drawing focus ??? */
400 FIXME (nonclient
, "undocumented flag (0x2000)!\n");
406 /***********************************************************************
407 * DrawCaptionTemp32W [USER32.602]
417 DrawCaptionTemp32W (HWND32 hwnd
, HDC32 hdc
, const RECT32
*rect
, HFONT32 hFont
,
418 HICON32 hIcon
, LPCWSTR str
, UINT32 uFlags
)
420 LPSTR p
= HEAP_strdupWtoA (GetProcessHeap (), 0, str
);
421 BOOL32 res
= DrawCaptionTemp32A (hwnd
, hdc
, rect
, hFont
, hIcon
, p
, uFlags
);
422 HeapFree (GetProcessHeap (), 0, p
);
427 /***********************************************************************
428 * AdjustWindowRect16 (USER.102)
430 BOOL16 WINAPI
AdjustWindowRect16( LPRECT16 rect
, DWORD style
, BOOL16 menu
)
432 return AdjustWindowRectEx16( rect
, style
, menu
, 0 );
436 /***********************************************************************
437 * AdjustWindowRect32 (USER32.2)
439 BOOL32 WINAPI
AdjustWindowRect32( LPRECT32 rect
, DWORD style
, BOOL32 menu
)
441 return AdjustWindowRectEx32( rect
, style
, menu
, 0 );
445 /***********************************************************************
446 * AdjustWindowRectEx16 (USER.454)
448 BOOL16 WINAPI
AdjustWindowRectEx16( LPRECT16 rect
, DWORD style
,
449 BOOL16 menu
, DWORD exStyle
)
451 /* Correct the window style */
453 if (!(style
& (WS_POPUP
| WS_CHILD
))) /* Overlapped window */
455 style
&= (WS_DLGFRAME
| WS_BORDER
| WS_THICKFRAME
| WS_CHILD
);
456 exStyle
&= (WS_EX_DLGMODALFRAME
| WS_EX_CLIENTEDGE
|
457 WS_EX_STATICEDGE
| WS_EX_TOOLWINDOW
);
458 if (exStyle
& WS_EX_DLGMODALFRAME
) style
&= ~WS_THICKFRAME
;
460 TRACE(nonclient
, "(%d,%d)-(%d,%d) %08lx %d %08lx\n",
461 rect
->left
, rect
->top
, rect
->right
, rect
->bottom
,
462 style
, menu
, exStyle
);
464 if (TWEAK_WineLook
== WIN31_LOOK
)
465 NC_AdjustRect( rect
, style
, menu
, exStyle
);
467 NC_AdjustRectOuter95( rect
, style
, menu
, exStyle
);
468 NC_AdjustRectInner95( rect
, style
, exStyle
);
475 /***********************************************************************
476 * AdjustWindowRectEx32 (USER32.3)
478 BOOL32 WINAPI
AdjustWindowRectEx32( LPRECT32 rect
, DWORD style
,
479 BOOL32 menu
, DWORD exStyle
)
484 CONV_RECT32TO16( rect
, &rect16
);
485 ret
= AdjustWindowRectEx16( &rect16
, style
, (BOOL16
)menu
, exStyle
);
486 CONV_RECT16TO32( &rect16
, rect
);
491 /***********************************************************************
492 * NC_HandleNCCalcSize
494 * Handle a WM_NCCALCSIZE message. Called from DefWindowProc().
496 LONG
NC_HandleNCCalcSize( WND
*pWnd
, RECT32
*winRect
)
498 RECT16 tmpRect
= { 0, 0, 0, 0 };
501 if (pWnd
->class->style
& CS_VREDRAW
) result
|= WVR_VREDRAW
;
502 if (pWnd
->class->style
& CS_HREDRAW
) result
|= WVR_HREDRAW
;
504 if( !( pWnd
->dwStyle
& WS_MINIMIZE
) ) {
505 if (TWEAK_WineLook
== WIN31_LOOK
)
506 NC_AdjustRect( &tmpRect
, pWnd
->dwStyle
, FALSE
, pWnd
->dwExStyle
);
508 NC_AdjustRectOuter95( &tmpRect
, pWnd
->dwStyle
, FALSE
, pWnd
->dwExStyle
);
510 winRect
->left
-= tmpRect
.left
;
511 winRect
->top
-= tmpRect
.top
;
512 winRect
->right
-= tmpRect
.right
;
513 winRect
->bottom
-= tmpRect
.bottom
;
515 if (HAS_MENU(pWnd
)) {
516 TRACE(nonclient
, "Calling "
517 "GetMenuBarHeight with HWND 0x%x, width %d, "
518 "at (%d, %d).\n", pWnd
->hwndSelf
,
519 winRect
->right
- winRect
->left
,
520 -tmpRect
.left
, -tmpRect
.top
);
523 MENU_GetMenuBarHeight( pWnd
->hwndSelf
,
524 winRect
->right
- winRect
->left
,
525 -tmpRect
.left
, -tmpRect
.top
) + 1;
528 if (TWEAK_WineLook
> WIN31_LOOK
) {
529 SetRect16 (&tmpRect
, 0, 0, 0, 0);
530 NC_AdjustRectInner95 (&tmpRect
, pWnd
->dwStyle
, pWnd
->dwExStyle
);
531 winRect
->left
-= tmpRect
.left
;
532 winRect
->top
-= tmpRect
.top
;
533 winRect
->right
-= tmpRect
.right
;
534 winRect
->bottom
-= tmpRect
.bottom
;
541 /***********************************************************************
544 * Get the 'inside' rectangle of a window, i.e. the whole window rectangle
545 * but without the borders (if any).
546 * The rectangle is in window coordinates (for drawing with GetWindowDC()).
548 static void NC_GetInsideRect( HWND32 hwnd
, RECT32
*rect
)
550 WND
* wndPtr
= WIN_FindWndPtr( hwnd
);
552 rect
->top
= rect
->left
= 0;
553 rect
->right
= wndPtr
->rectWindow
.right
- wndPtr
->rectWindow
.left
;
554 rect
->bottom
= wndPtr
->rectWindow
.bottom
- wndPtr
->rectWindow
.top
;
556 if ((wndPtr
->dwStyle
& WS_ICONIC
) || (wndPtr
->flags
& WIN_MANAGED
)) return;
558 /* Remove frame from rectangle */
559 if (HAS_DLGFRAME( wndPtr
->dwStyle
, wndPtr
->dwExStyle
))
561 InflateRect32( rect
, -SYSMETRICS_CXDLGFRAME
, -SYSMETRICS_CYDLGFRAME
);
562 if (wndPtr
->dwExStyle
& WS_EX_DLGMODALFRAME
)
563 InflateRect32( rect
, -1, 0 );
567 if (HAS_THICKFRAME( wndPtr
->dwStyle
))
568 InflateRect32( rect
, -SYSMETRICS_CXFRAME
, -SYSMETRICS_CYFRAME
);
569 if (wndPtr
->dwStyle
& WS_BORDER
)
570 InflateRect32( rect
, -SYSMETRICS_CXBORDER
, -SYSMETRICS_CYBORDER
);
577 /***********************************************************************
580 * Get the 'inside' rectangle of a window, i.e. the whole window rectangle
581 * but without the borders (if any).
582 * The rectangle is in window coordinates (for drawing with GetWindowDC()).
586 NC_GetInsideRect95 (HWND32 hwnd
, RECT32
*rect
)
588 WND
* wndPtr
= WIN_FindWndPtr( hwnd
);
590 rect
->top
= rect
->left
= 0;
591 rect
->right
= wndPtr
->rectWindow
.right
- wndPtr
->rectWindow
.left
;
592 rect
->bottom
= wndPtr
->rectWindow
.bottom
- wndPtr
->rectWindow
.top
;
594 if ((wndPtr
->dwStyle
& WS_ICONIC
) || (wndPtr
->flags
& WIN_MANAGED
)) return;
596 /* Remove frame from rectangle */
597 if (HAS_FIXEDFRAME (wndPtr
->dwStyle
, wndPtr
->dwExStyle
))
599 InflateRect32( rect
, -SYSMETRICS_CXFIXEDFRAME
, -SYSMETRICS_CYFIXEDFRAME
);
601 else if (HAS_SIZEFRAME (wndPtr
->dwStyle
))
603 InflateRect32( rect
, -SYSMETRICS_CXSIZEFRAME
, -SYSMETRICS_CYSIZEFRAME
);
605 /* if (wndPtr->dwStyle & WS_BORDER)
606 InflateRect32( rect, -SYSMETRICS_CXBORDER, -SYSMETRICS_CYBORDER );*/
609 if (wndPtr
->dwStyle
& WS_CHILD
) {
610 if (wndPtr
->dwExStyle
& WS_EX_CLIENTEDGE
)
611 InflateRect32 (rect
, -SYSMETRICS_CXEDGE
, -SYSMETRICS_CYEDGE
);
613 if (wndPtr
->dwExStyle
& WS_EX_STATICEDGE
)
614 InflateRect32 (rect
, -SYSMETRICS_CXBORDER
, -SYSMETRICS_CYBORDER
);
621 /***********************************************************************
624 * Handle a WM_NCHITTEST message. Called from NC_HandleNcHitTest().
627 LONG
NC_DoNCHitTest (WND
*wndPtr
, POINT16 pt
)
631 TRACE(nonclient
, "hwnd=%04x pt=%d,%d\n",
632 wndPtr
->hwndSelf
, pt
.x
, pt
.y
);
634 GetWindowRect16 (wndPtr
->hwndSelf
, &rect
);
635 if (!PtInRect16( &rect
, pt
)) return HTNOWHERE
;
637 if (wndPtr
->dwStyle
& WS_MINIMIZE
) return HTCAPTION
;
639 if (!(wndPtr
->flags
& WIN_MANAGED
))
642 if (HAS_THICKFRAME( wndPtr
->dwStyle
))
644 InflateRect16( &rect
, -SYSMETRICS_CXFRAME
, -SYSMETRICS_CYFRAME
);
645 if (wndPtr
->dwStyle
& WS_BORDER
)
646 InflateRect16(&rect
,-SYSMETRICS_CXBORDER
,-SYSMETRICS_CYBORDER
);
647 if (!PtInRect16( &rect
, pt
))
649 /* Check top sizing border */
652 if (pt
.x
< rect
.left
+SYSMETRICS_CXSIZE
) return HTTOPLEFT
;
653 if (pt
.x
>= rect
.right
-SYSMETRICS_CXSIZE
) return HTTOPRIGHT
;
656 /* Check bottom sizing border */
657 if (pt
.y
>= rect
.bottom
)
659 if (pt
.x
< rect
.left
+SYSMETRICS_CXSIZE
) return HTBOTTOMLEFT
;
660 if (pt
.x
>= rect
.right
-SYSMETRICS_CXSIZE
) return HTBOTTOMRIGHT
;
663 /* Check left sizing border */
664 if (pt
.x
< rect
.left
)
666 if (pt
.y
< rect
.top
+SYSMETRICS_CYSIZE
) return HTTOPLEFT
;
667 if (pt
.y
>= rect
.bottom
-SYSMETRICS_CYSIZE
) return HTBOTTOMLEFT
;
670 /* Check right sizing border */
671 if (pt
.x
>= rect
.right
)
673 if (pt
.y
< rect
.top
+SYSMETRICS_CYSIZE
) return HTTOPRIGHT
;
674 if (pt
.y
>= rect
.bottom
-SYSMETRICS_CYSIZE
) return HTBOTTOMRIGHT
;
679 else /* No thick frame */
681 if (HAS_DLGFRAME( wndPtr
->dwStyle
, wndPtr
->dwExStyle
))
682 InflateRect16(&rect
, -SYSMETRICS_CXDLGFRAME
, -SYSMETRICS_CYDLGFRAME
);
683 else if (wndPtr
->dwStyle
& WS_BORDER
)
684 InflateRect16(&rect
, -SYSMETRICS_CXBORDER
, -SYSMETRICS_CYBORDER
);
685 if (!PtInRect16( &rect
, pt
)) return HTBORDER
;
690 if ((wndPtr
->dwStyle
& WS_CAPTION
) == WS_CAPTION
)
692 rect
.top
+= sysMetrics
[SM_CYCAPTION
] - 1;
693 if (!PtInRect16( &rect
, pt
))
695 /* Check system menu */
696 if (wndPtr
->dwStyle
& WS_SYSMENU
)
697 rect
.left
+= SYSMETRICS_CXSIZE
;
698 if (pt
.x
<= rect
.left
) return HTSYSMENU
;
699 /* Check maximize box */
700 if (wndPtr
->dwStyle
& WS_MAXIMIZEBOX
)
701 rect
.right
-= SYSMETRICS_CXSIZE
+ 1;
702 if (pt
.x
>= rect
.right
) return HTMAXBUTTON
;
703 /* Check minimize box */
704 if (wndPtr
->dwStyle
& WS_MINIMIZEBOX
)
705 rect
.right
-= SYSMETRICS_CXSIZE
+ 1;
706 if (pt
.x
>= rect
.right
) return HTMINBUTTON
;
712 /* Check client area */
714 ScreenToClient16( wndPtr
->hwndSelf
, &pt
);
715 GetClientRect16( wndPtr
->hwndSelf
, &rect
);
716 if (PtInRect16( &rect
, pt
)) return HTCLIENT
;
718 /* Check vertical scroll bar */
720 if (wndPtr
->dwStyle
& WS_VSCROLL
)
722 rect
.right
+= SYSMETRICS_CXVSCROLL
;
723 if (PtInRect16( &rect
, pt
)) return HTVSCROLL
;
726 /* Check horizontal scroll bar */
728 if (wndPtr
->dwStyle
& WS_HSCROLL
)
730 rect
.bottom
+= SYSMETRICS_CYHSCROLL
;
731 if (PtInRect16( &rect
, pt
))
734 if ((wndPtr
->dwStyle
& WS_VSCROLL
) &&
735 (pt
.x
>= rect
.right
- SYSMETRICS_CXVSCROLL
))
743 if (HAS_MENU(wndPtr
))
745 if ((pt
.y
< 0) && (pt
.x
>= 0) && (pt
.x
< rect
.right
))
749 /* Should never get here */
754 /***********************************************************************
757 * Handle a WM_NCHITTEST message. Called from NC_HandleNCHitTest().
759 * FIXME: Just a modified copy of the Win 3.1 version.
763 NC_DoNCHitTest95 (WND
*wndPtr
, POINT16 pt
)
767 TRACE(nonclient
, "hwnd=%04x pt=%d,%d\n",
768 wndPtr
->hwndSelf
, pt
.x
, pt
.y
);
770 GetWindowRect16 (wndPtr
->hwndSelf
, &rect
);
771 if (!PtInRect16( &rect
, pt
)) return HTNOWHERE
;
773 if (wndPtr
->dwStyle
& WS_MINIMIZE
) return HTCAPTION
;
775 if (!(wndPtr
->flags
& WIN_MANAGED
))
778 if (HAS_SIZEFRAME( wndPtr
->dwStyle
))
780 InflateRect16( &rect
, -SYSMETRICS_CXFRAME
, -SYSMETRICS_CYFRAME
);
781 /* if (wndPtr->dwStyle & WS_BORDER) */
782 /* InflateRect16(&rect,-SYSMETRICS_CXBORDER,-SYSMETRICS_CYBORDER); */
783 if (!PtInRect16( &rect
, pt
))
785 /* Check top sizing border */
788 if (pt
.x
< rect
.left
+SYSMETRICS_CXSIZE
) return HTTOPLEFT
;
789 if (pt
.x
>= rect
.right
-SYSMETRICS_CXSIZE
) return HTTOPRIGHT
;
792 /* Check bottom sizing border */
793 if (pt
.y
>= rect
.bottom
)
795 if (pt
.x
< rect
.left
+SYSMETRICS_CXSIZE
) return HTBOTTOMLEFT
;
796 if (pt
.x
>= rect
.right
-SYSMETRICS_CXSIZE
) return HTBOTTOMRIGHT
;
799 /* Check left sizing border */
800 if (pt
.x
< rect
.left
)
802 if (pt
.y
< rect
.top
+SYSMETRICS_CYSIZE
) return HTTOPLEFT
;
803 if (pt
.y
>= rect
.bottom
-SYSMETRICS_CYSIZE
) return HTBOTTOMLEFT
;
806 /* Check right sizing border */
807 if (pt
.x
>= rect
.right
)
809 if (pt
.y
< rect
.top
+SYSMETRICS_CYSIZE
) return HTTOPRIGHT
;
810 if (pt
.y
>= rect
.bottom
-SYSMETRICS_CYSIZE
) return HTBOTTOMRIGHT
;
815 else /* No thick frame */
817 if (HAS_FIXEDFRAME( wndPtr
->dwStyle
, wndPtr
->dwExStyle
))
818 InflateRect16(&rect
, -SYSMETRICS_CXDLGFRAME
, -SYSMETRICS_CYDLGFRAME
);
819 /* else if (wndPtr->dwStyle & WS_BORDER) */
820 /* InflateRect16(&rect, -SYSMETRICS_CXBORDER, -SYSMETRICS_CYBORDER); */
821 if (!PtInRect16( &rect
, pt
)) return HTBORDER
;
826 if ((wndPtr
->dwStyle
& WS_CAPTION
) == WS_CAPTION
)
828 if (wndPtr
->dwExStyle
& WS_EX_TOOLWINDOW
)
829 rect
.top
+= sysMetrics
[SM_CYSMCAPTION
] - 1;
831 rect
.top
+= sysMetrics
[SM_CYCAPTION
] - 1;
832 if (!PtInRect16( &rect
, pt
))
834 /* Check system menu */
835 if ((wndPtr
->dwStyle
& WS_SYSMENU
) &&
836 ((wndPtr
->class->hIconSm
) || (wndPtr
->class->hIcon
)))
837 rect
.left
+= sysMetrics
[SM_CYCAPTION
] - 1;
838 if (pt
.x
< rect
.left
) return HTSYSMENU
;
840 /* Check close button */
841 if (wndPtr
->dwStyle
& WS_SYSMENU
)
842 rect
.right
-= sysMetrics
[SM_CYCAPTION
] - 1;
843 if (pt
.x
> rect
.right
) return HTCLOSE
;
845 /* Check maximize box */
846 if (wndPtr
->dwStyle
& WS_MAXIMIZEBOX
)
847 rect
.right
-= SYSMETRICS_CXSIZE
+ 1;
848 if (pt
.x
> rect
.right
) return HTMAXBUTTON
;
850 /* Check minimize box */
851 if (wndPtr
->dwStyle
& WS_MINIMIZEBOX
)
852 rect
.right
-= SYSMETRICS_CXSIZE
+ 1;
853 if (pt
.x
> rect
.right
) return HTMINBUTTON
;
859 /* Check client area */
861 ScreenToClient16( wndPtr
->hwndSelf
, &pt
);
862 GetClientRect16( wndPtr
->hwndSelf
, &rect
);
863 if (PtInRect16( &rect
, pt
)) return HTCLIENT
;
865 /* Check vertical scroll bar */
867 if (wndPtr
->dwStyle
& WS_VSCROLL
)
869 rect
.right
+= SYSMETRICS_CXVSCROLL
;
870 if (PtInRect16( &rect
, pt
)) return HTVSCROLL
;
873 /* Check horizontal scroll bar */
875 if (wndPtr
->dwStyle
& WS_HSCROLL
)
877 rect
.bottom
+= SYSMETRICS_CYHSCROLL
;
878 if (PtInRect16( &rect
, pt
))
881 if ((wndPtr
->dwStyle
& WS_VSCROLL
) &&
882 (pt
.x
>= rect
.right
- SYSMETRICS_CXVSCROLL
))
890 if (HAS_MENU(wndPtr
))
892 if ((pt
.y
< 0) && (pt
.x
>= 0) && (pt
.x
< rect
.right
))
896 /* Should never get here */
901 /***********************************************************************
904 * Handle a WM_NCHITTEST message. Called from DefWindowProc().
907 NC_HandleNCHitTest (HWND32 hwnd
, POINT16 pt
)
909 WND
*wndPtr
= WIN_FindWndPtr (hwnd
);
914 if (TWEAK_WineLook
== WIN31_LOOK
)
915 return NC_DoNCHitTest (wndPtr
, pt
);
917 return NC_DoNCHitTest95 (wndPtr
, pt
);
921 /***********************************************************************
924 void NC_DrawSysButton( HWND32 hwnd
, HDC32 hdc
, BOOL32 down
)
929 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
931 if( !(wndPtr
->flags
& WIN_MANAGED
) )
933 NC_GetInsideRect( hwnd
, &rect
);
934 hdcMem
= CreateCompatibleDC32( hdc
);
935 hbitmap
= SelectObject32( hdcMem
, hbitmapClose
);
936 BitBlt32(hdc
, rect
.left
, rect
.top
, SYSMETRICS_CXSIZE
, SYSMETRICS_CYSIZE
,
937 hdcMem
, (wndPtr
->dwStyle
& WS_CHILD
) ? SYSMETRICS_CXSIZE
: 0, 0,
938 down
? NOTSRCCOPY
: SRCCOPY
);
939 SelectObject32( hdcMem
, hbitmap
);
940 DeleteDC32( hdcMem
);
945 /***********************************************************************
948 static void NC_DrawMaxButton( HWND32 hwnd
, HDC16 hdc
, BOOL32 down
)
951 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
954 if( !(wndPtr
->flags
& WIN_MANAGED
) )
956 NC_GetInsideRect( hwnd
, &rect
);
957 hdcMem
= CreateCompatibleDC32( hdc
);
958 SelectObject32( hdcMem
, (IsZoomed32(hwnd
)
959 ? (down
? hbitmapRestoreD
: hbitmapRestore
)
960 : (down
? hbitmapMaximizeD
: hbitmapMaximize
)) );
961 BitBlt32( hdc
, rect
.right
- SYSMETRICS_CXSIZE
- 1, rect
.top
,
962 SYSMETRICS_CXSIZE
+ 1, SYSMETRICS_CYSIZE
, hdcMem
, 0, 0,
964 DeleteDC32( hdcMem
);
969 /***********************************************************************
972 static void NC_DrawMinButton( HWND32 hwnd
, HDC16 hdc
, BOOL32 down
)
975 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
978 if( !(wndPtr
->flags
& WIN_MANAGED
) )
980 NC_GetInsideRect( hwnd
, &rect
);
981 hdcMem
= CreateCompatibleDC32( hdc
);
982 SelectObject32( hdcMem
, (down
? hbitmapMinimizeD
: hbitmapMinimize
) );
983 if (wndPtr
->dwStyle
& WS_MAXIMIZEBOX
) rect
.right
-= SYSMETRICS_CXSIZE
+1;
984 BitBlt32( hdc
, rect
.right
- SYSMETRICS_CXSIZE
- 1, rect
.top
,
985 SYSMETRICS_CXSIZE
+ 1, SYSMETRICS_CYSIZE
, hdcMem
, 0, 0,
987 DeleteDC32( hdcMem
);
992 /******************************************************************************
994 * void NC_DrawSysButton95(
999 * Draws the Win95 system icon.
1002 * 05-Jul-1997 Dave Cuthbert (dacut@ece.cmu.edu)
1003 * Original implementation from NC_DrawSysButton source.
1004 * 11-Jun-1998 Eric Kohl (ekohl@abo.rhein-zeitung.de)
1007 *****************************************************************************/
1010 NC_DrawSysButton95 (HWND32 hwnd
, HDC32 hdc
, BOOL32 down
)
1012 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
1014 if( !(wndPtr
->flags
& WIN_MANAGED
) )
1019 NC_GetInsideRect95( hwnd
, &rect
);
1021 if (wndPtr
->class->hIconSm
)
1022 hIcon
= wndPtr
->class->hIconSm
;
1023 else if (wndPtr
->class->hIcon
)
1024 hIcon
= wndPtr
->class->hIcon
;
1027 DrawIconEx32 (hdc
, rect
.left
+ 2, rect
.top
+ 2, hIcon
,
1028 sysMetrics
[SM_CXSMICON
],
1029 sysMetrics
[SM_CYSMICON
],
1032 return (hIcon
!= 0);
1038 /******************************************************************************
1040 * void NC_DrawCloseButton95(
1045 * Draws the Win95 close button.
1048 * 11-Jun-1998 Eric Kohl (ekohl@abo.rhein-zeitung.de)
1049 * Original implementation from NC_DrawSysButton95 source.
1051 *****************************************************************************/
1054 NC_DrawCloseButton95 (HWND32 hwnd
, HDC32 hdc
, BOOL32 down
)
1058 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
1060 if( !(wndPtr
->flags
& WIN_MANAGED
) )
1063 HBITMAP32 hBmp
, hOldBmp
;
1065 NC_GetInsideRect95( hwnd
, &rect
);
1067 hdcMem
= CreateCompatibleDC32( hdc
);
1068 hBmp
= /*down ? hbitmapCloseD :*/ hbitmapClose
;
1069 hOldBmp
= SelectObject32 (hdcMem
, hBmp
);
1070 GetObject32A (hBmp
, sizeof(BITMAP32
), &bmp
);
1071 BitBlt32 (hdc
, rect
.right
- (sysMetrics
[SM_CYCAPTION
] + 1 + bmp
.bmWidth
) / 2,
1072 rect
.top
+ (sysMetrics
[SM_CYCAPTION
] - 1 - bmp
.bmHeight
) / 2,
1073 bmp
.bmWidth
, bmp
.bmHeight
, hdcMem
, 0, 0, down
? NOTSRCCOPY
: SRCCOPY
);
1075 SelectObject32 (hdcMem
, hOldBmp
);
1076 DeleteDC32 (hdcMem
);
1081 /******************************************************************************
1083 * NC_DrawMaxButton95(
1088 * Draws the maximize button for Win95 style windows.
1091 * Many. Spacing might still be incorrect. Need to fit a close
1092 * button between the max button and the edge.
1093 * Should scale the image with the title bar. And more...
1096 * 05-Jul-1997 Dave Cuthbert (dacut@ece.cmu.edu)
1097 * Original implementation.
1099 *****************************************************************************/
1101 static void NC_DrawMaxButton95(
1107 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
1112 if( !(wndPtr
->flags
& WIN_MANAGED
) &&
1113 GetBitmapDimensionEx32((bm
= IsZoomed32(hwnd
) ?
1114 (down
? hbitmapRestoreD
: hbitmapRestore
) :
1115 (down
? hbitmapMaximizeD
: hbitmapMaximize
)),
1118 NC_GetInsideRect95( hwnd
, &rect
);
1120 if (wndPtr
->dwStyle
& WS_SYSMENU
)
1121 rect
.right
-= sysMetrics
[SM_CYCAPTION
] + 1;
1123 hdcMem
= CreateCompatibleDC32( hdc
);
1124 SelectObject32( hdc
, bm
);
1125 BitBlt32( hdc
, rect
.right
- (sysMetrics
[SM_CXSIZE
] + bmsz
.cx
) / 2,
1126 rect
.top
+ (sysMetrics
[SM_CYCAPTION
] - 1 - bmsz
.cy
) / 2,
1127 bmsz
.cx
, bmsz
.cy
, hdcMem
, 0, 0, SRCCOPY
);
1128 DeleteDC32( hdcMem
);
1135 /******************************************************************************
1137 * NC_DrawMinButton95(
1142 * Draws the minimize button for Win95 style windows.
1145 * Many. Spacing is still incorrect. Should scale the image with the
1146 * title bar. And more...
1149 * 05-Jul-1997 Dave Cuthbert (dacut@ece.cmu.edu)
1150 * Original implementation.
1152 *****************************************************************************/
1154 static void NC_DrawMinButton95(
1160 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
1165 if( !(wndPtr
->flags
& WIN_MANAGED
) &&
1166 GetBitmapDimensionEx32((bm
= down
? hbitmapMinimizeD
:
1167 hbitmapMinimize
), &bmsz
)) {
1169 NC_GetInsideRect95( hwnd
, &rect
);
1171 if (wndPtr
->dwStyle
& WS_SYSMENU
)
1172 rect
.right
-= sysMetrics
[SM_CYCAPTION
] + 1;
1174 if (wndPtr
->dwStyle
& WS_MAXIMIZEBOX
)
1176 (sysMetrics
[SM_CXSIZE
] + bmsz
.cx
) / 2;
1178 hdcMem
= CreateCompatibleDC32( hdc
);
1179 SelectObject32( hdc
, bm
);
1180 BitBlt32( hdc
, rect
.right
- (sysMetrics
[SM_CXSIZE
] + bmsz
.cx
) / 2,
1181 rect
.top
+ (sysMetrics
[SM_CYCAPTION
] - 1 - bmsz
.cy
) / 2,
1182 bmsz
.cx
, bmsz
.cy
, hdcMem
, 0, 0, SRCCOPY
);
1183 DeleteDC32( hdcMem
);
1190 /***********************************************************************
1193 * Draw a window frame inside the given rectangle, and update the rectangle.
1194 * The correct pen for the frame must be selected in the DC.
1196 static void NC_DrawFrame( HDC32 hdc
, RECT32
*rect
, BOOL32 dlgFrame
,
1199 INT32 width
, height
;
1201 if (TWEAK_WineLook
!= WIN31_LOOK
)
1202 ERR (nonclient
, "Called in Win95 mode. Aiee! Please report this.\n" );
1206 width
= SYSMETRICS_CXDLGFRAME
- 1;
1207 height
= SYSMETRICS_CYDLGFRAME
- 1;
1208 SelectObject32( hdc
, GetSysColorBrush32(active
? COLOR_ACTIVECAPTION
:
1209 COLOR_INACTIVECAPTION
) );
1213 width
= SYSMETRICS_CXFRAME
- 1;
1214 height
= SYSMETRICS_CYFRAME
- 1;
1215 SelectObject32( hdc
, GetSysColorBrush32(active
? COLOR_ACTIVEBORDER
:
1216 COLOR_INACTIVEBORDER
) );
1220 PatBlt32( hdc
, rect
->left
, rect
->top
,
1221 rect
->right
- rect
->left
, height
, PATCOPY
);
1222 PatBlt32( hdc
, rect
->left
, rect
->top
,
1223 width
, rect
->bottom
- rect
->top
, PATCOPY
);
1224 PatBlt32( hdc
, rect
->left
, rect
->bottom
,
1225 rect
->right
- rect
->left
, -height
, PATCOPY
);
1226 PatBlt32( hdc
, rect
->right
, rect
->top
,
1227 -width
, rect
->bottom
- rect
->top
, PATCOPY
);
1231 InflateRect32( rect
, -width
, -height
);
1235 INT32 decYOff
= SYSMETRICS_CXFRAME
+ SYSMETRICS_CXSIZE
;
1236 INT32 decXOff
= SYSMETRICS_CYFRAME
+ SYSMETRICS_CYSIZE
;
1238 /* Draw inner rectangle */
1240 SelectObject32( hdc
, GetStockObject32(NULL_BRUSH
) );
1241 Rectangle32( hdc
, rect
->left
+ width
, rect
->top
+ height
,
1242 rect
->right
- width
, rect
->bottom
- height
);
1244 /* Draw the decorations */
1246 MoveToEx32( hdc
, rect
->left
, rect
->top
+ decYOff
, NULL
);
1247 LineTo32( hdc
, rect
->left
+ width
, rect
->top
+ decYOff
);
1248 MoveToEx32( hdc
, rect
->right
- 1, rect
->top
+ decYOff
, NULL
);
1249 LineTo32( hdc
, rect
->right
- width
- 1, rect
->top
+ decYOff
);
1250 MoveToEx32( hdc
, rect
->left
, rect
->bottom
- decYOff
, NULL
);
1251 LineTo32( hdc
, rect
->left
+ width
, rect
->bottom
- decYOff
);
1252 MoveToEx32( hdc
, rect
->right
- 1, rect
->bottom
- decYOff
, NULL
);
1253 LineTo32( hdc
, rect
->right
- width
- 1, rect
->bottom
- decYOff
);
1255 MoveToEx32( hdc
, rect
->left
+ decXOff
, rect
->top
, NULL
);
1256 LineTo32( hdc
, rect
->left
+ decXOff
, rect
->top
+ height
);
1257 MoveToEx32( hdc
, rect
->left
+ decXOff
, rect
->bottom
- 1, NULL
);
1258 LineTo32( hdc
, rect
->left
+ decXOff
, rect
->bottom
- height
- 1 );
1259 MoveToEx32( hdc
, rect
->right
- decXOff
, rect
->top
, NULL
);
1260 LineTo32( hdc
, rect
->right
- decXOff
, rect
->top
+ height
);
1261 MoveToEx32( hdc
, rect
->right
- decXOff
, rect
->bottom
- 1, NULL
);
1262 LineTo32( hdc
, rect
->right
- decXOff
, rect
->bottom
- height
- 1 );
1264 InflateRect32( rect
, -width
- 1, -height
- 1 );
1269 /******************************************************************************
1271 * void NC_DrawFrame95(
1277 * Draw a window frame inside the given rectangle, and update the rectangle.
1278 * The correct pen for the frame must be selected in the DC.
1281 * Many. First, just what IS a frame in Win95? Note that the 3D look
1282 * on the outer edge is handled by NC_DoNCPaint95. As is the inner
1283 * edge. The inner rectangle just inside the frame is handled by the
1286 * In short, for most people, this function should be a nop (unless
1287 * you LIKE thick borders in Win95/NT4.0 -- I've been working with
1288 * them lately, but just to get this code right). Even so, it doesn't
1289 * appear to be so. It's being worked on...
1292 * 06-Jul-1997 Dave Cuthbert (dacut@ece.cmu.edu)
1293 * Original implementation (based on NC_DrawFrame)
1294 * 02-Jun-1998 Eric Kohl (ekohl@abo.rhein-zeitung.de)
1297 *****************************************************************************/
1299 static void NC_DrawFrame95(
1305 INT32 width
, height
;
1309 width
= sysMetrics
[SM_CXDLGFRAME
] - sysMetrics
[SM_CXEDGE
];
1310 height
= sysMetrics
[SM_CYDLGFRAME
] - sysMetrics
[SM_CYEDGE
];
1314 width
= sysMetrics
[SM_CXFRAME
] - sysMetrics
[SM_CXEDGE
];
1315 height
= sysMetrics
[SM_CYFRAME
] - sysMetrics
[SM_CYEDGE
];
1318 SelectObject32( hdc
, GetSysColorBrush32(active
? COLOR_ACTIVEBORDER
:
1319 COLOR_INACTIVEBORDER
) );
1322 PatBlt32( hdc
, rect
->left
, rect
->top
,
1323 rect
->right
- rect
->left
, height
, PATCOPY
);
1324 PatBlt32( hdc
, rect
->left
, rect
->top
,
1325 width
, rect
->bottom
- rect
->top
, PATCOPY
);
1326 PatBlt32( hdc
, rect
->left
, rect
->bottom
,
1327 rect
->right
- rect
->left
, -height
, PATCOPY
);
1328 PatBlt32( hdc
, rect
->right
, rect
->top
,
1329 -width
, rect
->bottom
- rect
->top
, PATCOPY
);
1331 InflateRect32( rect
, -width
, -height
);
1336 /***********************************************************************
1337 * NC_DrawMovingFrame
1339 * Draw the frame used when moving or resizing window.
1341 * FIXME: This causes problems in Win95 mode. (why?)
1343 static void NC_DrawMovingFrame( HDC32 hdc
, RECT32
*rect
, BOOL32 thickframe
)
1348 CONV_RECT32TO16( rect
, &r16
);
1349 FastWindowFrame( hdc
, &r16
, SYSMETRICS_CXFRAME
,
1350 SYSMETRICS_CYFRAME
, PATINVERT
);
1352 else DrawFocusRect32( hdc
, rect
);
1356 /***********************************************************************
1359 * Draw the window caption.
1360 * The correct pen for the window frame must be selected in the DC.
1362 static void NC_DrawCaption( HDC32 hdc
, RECT32
*rect
, HWND32 hwnd
,
1363 DWORD style
, BOOL32 active
)
1366 WND
* wndPtr
= WIN_FindWndPtr( hwnd
);
1369 if (wndPtr
->flags
& WIN_MANAGED
) return;
1373 if (!(hbitmapClose
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_CLOSE
) )))
1375 hbitmapCloseD
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_CLOSE
) );
1376 hbitmapMinimize
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_REDUCE
) );
1377 hbitmapMinimizeD
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_REDUCED
) );
1378 hbitmapMaximize
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_ZOOM
) );
1379 hbitmapMaximizeD
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_ZOOMD
) );
1380 hbitmapRestore
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_RESTORE
) );
1381 hbitmapRestoreD
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_RESTORED
) );
1384 if (wndPtr
->dwExStyle
& WS_EX_DLGMODALFRAME
)
1386 HBRUSH32 hbrushOld
= SelectObject32(hdc
, GetSysColorBrush32(COLOR_WINDOW
) );
1387 PatBlt32( hdc
, r
.left
, r
.top
, 1, r
.bottom
-r
.top
+1,PATCOPY
);
1388 PatBlt32( hdc
, r
.right
-1, r
.top
, 1, r
.bottom
-r
.top
+1, PATCOPY
);
1389 PatBlt32( hdc
, r
.left
, r
.top
-1, r
.right
-r
.left
, 1, PATCOPY
);
1392 SelectObject32( hdc
, hbrushOld
);
1395 MoveTo( hdc
, r
.left
, r
.bottom
);
1396 LineTo32( hdc
, r
.right
, r
.bottom
);
1398 if (style
& WS_SYSMENU
)
1400 NC_DrawSysButton( hwnd
, hdc
, FALSE
);
1401 r
.left
+= SYSMETRICS_CXSIZE
+ 1;
1402 MoveTo( hdc
, r
.left
- 1, r
.top
);
1403 LineTo32( hdc
, r
.left
- 1, r
.bottom
);
1405 if (style
& WS_MAXIMIZEBOX
)
1407 NC_DrawMaxButton( hwnd
, hdc
, FALSE
);
1408 r
.right
-= SYSMETRICS_CXSIZE
+ 1;
1410 if (style
& WS_MINIMIZEBOX
)
1412 NC_DrawMinButton( hwnd
, hdc
, FALSE
);
1413 r
.right
-= SYSMETRICS_CXSIZE
+ 1;
1416 FillRect32( hdc
, &r
, GetSysColorBrush32(active
? COLOR_ACTIVECAPTION
:
1417 COLOR_INACTIVECAPTION
) );
1419 if (GetWindowText32A( hwnd
, buffer
, sizeof(buffer
) ))
1421 if (active
) SetTextColor32( hdc
, GetSysColor32( COLOR_CAPTIONTEXT
) );
1422 else SetTextColor32( hdc
, GetSysColor32( COLOR_INACTIVECAPTIONTEXT
) );
1423 SetBkMode32( hdc
, TRANSPARENT
);
1424 DrawText32A( hdc
, buffer
, -1, &r
,
1425 DT_SINGLELINE
| DT_CENTER
| DT_VCENTER
| DT_NOPREFIX
);
1430 /******************************************************************************
1439 * Draw the window caption for Win95 style windows.
1440 * The correct pen for the window frame must be selected in the DC.
1443 * Hey, a function that finally works! Well, almost.
1444 * It's being worked on.
1447 * 05-Jul-1997 Dave Cuthbert (dacut@ece.cmu.edu)
1448 * Original implementation.
1449 * 02-Jun-1998 Eric Kohl (ekohl@abo.rhein-zeitung.de)
1452 *****************************************************************************/
1454 static void NC_DrawCaption95(
1463 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
1467 if (wndPtr
->flags
& WIN_MANAGED
) return;
1469 hPrevPen
= SelectObject32( hdc
, GetSysColorPen32(COLOR_3DFACE
) );
1470 MoveToEx32( hdc
, r
.left
, r
.bottom
- 1, NULL
);
1471 LineTo32( hdc
, r
.right
, r
.bottom
- 1 );
1472 SelectObject32( hdc
, hPrevPen
);
1475 FillRect32( hdc
, &r
, GetSysColorBrush32(active
? COLOR_ACTIVECAPTION
:
1476 COLOR_INACTIVECAPTION
) );
1478 if (!hbitmapClose
) {
1479 if (!(hbitmapClose
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_CLOSE
) )))
1481 hbitmapMinimize
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_REDUCE
) );
1482 hbitmapMinimizeD
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_REDUCED
) );
1483 hbitmapMaximize
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_ZOOM
) );
1484 hbitmapMaximizeD
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_ZOOMD
) );
1485 hbitmapRestore
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_RESTORE
) );
1486 hbitmapRestoreD
= LoadBitmap16( 0, MAKEINTRESOURCE16(OBM_RESTORED
) );
1489 if ((style
& WS_SYSMENU
) && !(exStyle
& WS_EX_TOOLWINDOW
)) {
1490 if (NC_DrawSysButton95 (hwnd
, hdc
, FALSE
))
1491 r
.left
+= sysMetrics
[SM_CYCAPTION
] - 1;
1493 if (style
& WS_SYSMENU
) {
1494 NC_DrawCloseButton95 (hwnd
, hdc
, FALSE
);
1495 r
.right
-= sysMetrics
[SM_CYCAPTION
] - 1;
1497 if (style
& WS_MAXIMIZEBOX
) {
1498 NC_DrawMaxButton95( hwnd
, hdc
, FALSE
);
1499 r
.right
-= SYSMETRICS_CXSIZE
+ 1;
1501 if (style
& WS_MINIMIZEBOX
) {
1502 NC_DrawMinButton95( hwnd
, hdc
, FALSE
);
1503 r
.right
-= SYSMETRICS_CXSIZE
+ 1;
1506 if (GetWindowText32A( hwnd
, buffer
, sizeof(buffer
) )) {
1507 NONCLIENTMETRICS32A nclm
;
1508 HFONT32 hFont
, hOldFont
;
1509 nclm
.cbSize
= sizeof(NONCLIENTMETRICS32A
);
1510 SystemParametersInfo32A (SPI_GETNONCLIENTMETRICS
, 0, &nclm
, 0);
1511 if (exStyle
& WS_EX_TOOLWINDOW
)
1512 hFont
= CreateFontIndirect32A (&nclm
.lfSmCaptionFont
);
1514 hFont
= CreateFontIndirect32A (&nclm
.lfCaptionFont
);
1515 hOldFont
= SelectObject32 (hdc
, hFont
);
1516 if (active
) SetTextColor32( hdc
, GetSysColor32( COLOR_CAPTIONTEXT
) );
1517 else SetTextColor32( hdc
, GetSysColor32( COLOR_INACTIVECAPTIONTEXT
) );
1518 SetBkMode32( hdc
, TRANSPARENT
);
1520 DrawText32A( hdc
, buffer
, -1, &r
,
1521 DT_SINGLELINE
| DT_VCENTER
| DT_NOPREFIX
| DT_LEFT
);
1522 DeleteObject32 (SelectObject32 (hdc
, hOldFont
));
1528 /***********************************************************************
1531 * Paint the non-client area. clip is currently unused.
1533 void NC_DoNCPaint( WND
* wndPtr
, HRGN32 clip
, BOOL32 suppress_menupaint
)
1538 HWND32 hwnd
= wndPtr
->hwndSelf
;
1540 if ( wndPtr
->dwStyle
& WS_MINIMIZE
||
1541 !WIN_IsWindowDrawable( wndPtr
, 0 )) return; /* Nothing to do */
1543 active
= wndPtr
->flags
& WIN_NCACTIVATED
;
1545 TRACE(nonclient
, "%04x %d\n", hwnd
, active
);
1547 if (!(hdc
= GetDCEx32( hwnd
, 0, DCX_USESTYLE
| DCX_WINDOW
))) return;
1549 if (ExcludeVisRect( hdc
, wndPtr
->rectClient
.left
-wndPtr
->rectWindow
.left
,
1550 wndPtr
->rectClient
.top
-wndPtr
->rectWindow
.top
,
1551 wndPtr
->rectClient
.right
-wndPtr
->rectWindow
.left
,
1552 wndPtr
->rectClient
.bottom
-wndPtr
->rectWindow
.top
)
1555 ReleaseDC32( hwnd
, hdc
);
1559 rect
.top
= rect
.left
= 0;
1560 rect
.right
= wndPtr
->rectWindow
.right
- wndPtr
->rectWindow
.left
;
1561 rect
.bottom
= wndPtr
->rectWindow
.bottom
- wndPtr
->rectWindow
.top
;
1563 SelectObject32( hdc
, GetSysColorPen32(COLOR_WINDOWFRAME
) );
1565 if (!(wndPtr
->flags
& WIN_MANAGED
))
1567 if ((wndPtr
->dwStyle
& WS_BORDER
) || (wndPtr
->dwStyle
& WS_DLGFRAME
) ||
1568 (wndPtr
->dwExStyle
& WS_EX_DLGMODALFRAME
))
1570 SelectObject32( hdc
, GetStockObject32(NULL_BRUSH
) );
1571 Rectangle32( hdc
, 0, 0, rect
.right
, rect
.bottom
);
1572 InflateRect32( &rect
, -1, -1 );
1575 if (HAS_DLGFRAME( wndPtr
->dwStyle
, wndPtr
->dwExStyle
))
1576 NC_DrawFrame( hdc
, &rect
, TRUE
, active
);
1577 else if (wndPtr
->dwStyle
& WS_THICKFRAME
)
1578 NC_DrawFrame(hdc
, &rect
, FALSE
, active
);
1580 if ((wndPtr
->dwStyle
& WS_CAPTION
) == WS_CAPTION
)
1583 r
.bottom
= rect
.top
+ SYSMETRICS_CYSIZE
;
1584 rect
.top
+= SYSMETRICS_CYSIZE
+ SYSMETRICS_CYBORDER
;
1585 NC_DrawCaption( hdc
, &r
, hwnd
, wndPtr
->dwStyle
, active
);
1589 if (HAS_MENU(wndPtr
))
1592 r
.bottom
= rect
.top
+ SYSMETRICS_CYMENU
; /* default height */
1593 rect
.top
+= MENU_DrawMenuBar( hdc
, &r
, hwnd
, suppress_menupaint
);
1596 /* Draw the scroll-bars */
1598 if (wndPtr
->dwStyle
& WS_VSCROLL
)
1599 SCROLL_DrawScrollBar( hwnd
, hdc
, SB_VERT
, TRUE
, TRUE
);
1600 if (wndPtr
->dwStyle
& WS_HSCROLL
)
1601 SCROLL_DrawScrollBar( hwnd
, hdc
, SB_HORZ
, TRUE
, TRUE
);
1603 /* Draw the "size-box" */
1605 if ((wndPtr
->dwStyle
& WS_VSCROLL
) && (wndPtr
->dwStyle
& WS_HSCROLL
))
1608 r
.left
= r
.right
- SYSMETRICS_CXVSCROLL
+ 1;
1609 r
.top
= r
.bottom
- SYSMETRICS_CYHSCROLL
+ 1;
1610 if(wndPtr
->dwStyle
& WS_BORDER
) {
1614 FillRect32( hdc
, &r
, GetSysColorBrush32(COLOR_SCROLLBAR
) );
1617 ReleaseDC32( hwnd
, hdc
);
1621 /******************************************************************************
1623 * void NC_DoNCPaint95(
1626 * BOOL32 suppress_menupaint )
1628 * Paint the non-client area for Win95 windows. The clip region is
1629 * currently ignored.
1632 * grep -E -A10 -B5 \(95\)\|\(Bugs\)\|\(FIXME\) windows/nonclient.c \
1633 * misc/tweak.c controls/menu.c # :-)
1636 * 03-Jul-1997 Dave Cuthbert (dacut@ece.cmu.edu)
1637 * Original implementation
1638 * 10-Jun-1998 Eric Kohl (ekohl@abo.rhein-zeitung.de)
1641 *****************************************************************************/
1643 void NC_DoNCPaint95(
1646 BOOL32 suppress_menupaint
)
1651 HWND32 hwnd
= wndPtr
->hwndSelf
;
1653 if ( wndPtr
->dwStyle
& WS_MINIMIZE
||
1654 !WIN_IsWindowDrawable( wndPtr
, 0 )) return; /* Nothing to do */
1656 active
= wndPtr
->flags
& WIN_NCACTIVATED
;
1658 TRACE(nonclient
, "%04x %d\n", hwnd
, active
);
1660 if (!(hdc
= GetDCEx32( hwnd
, 0, DCX_USESTYLE
| DCX_WINDOW
))) return;
1662 if (ExcludeVisRect( hdc
, wndPtr
->rectClient
.left
-wndPtr
->rectWindow
.left
,
1663 wndPtr
->rectClient
.top
-wndPtr
->rectWindow
.top
,
1664 wndPtr
->rectClient
.right
-wndPtr
->rectWindow
.left
,
1665 wndPtr
->rectClient
.bottom
-wndPtr
->rectWindow
.top
)
1668 ReleaseDC32( hwnd
, hdc
);
1672 rect
.top
= rect
.left
= 0;
1673 rect
.right
= wndPtr
->rectWindow
.right
- wndPtr
->rectWindow
.left
;
1674 rect
.bottom
= wndPtr
->rectWindow
.bottom
- wndPtr
->rectWindow
.top
;
1676 SelectObject32( hdc
, GetSysColorPen32(COLOR_WINDOWFRAME
) );
1678 if(!(wndPtr
->flags
& WIN_MANAGED
)) {
1679 if ((wndPtr
->dwStyle
& WS_BORDER
) && ((wndPtr
->dwStyle
& WS_DLGFRAME
) ||
1680 (wndPtr
->dwExStyle
& WS_EX_DLGMODALFRAME
) || (wndPtr
->dwStyle
& WS_THICKFRAME
))) {
1681 DrawEdge32 (hdc
, &rect
, EDGE_RAISED
, BF_RECT
| BF_ADJUST
);
1684 if (HAS_FIXEDFRAME( wndPtr
->dwStyle
, wndPtr
->dwExStyle
))
1685 NC_DrawFrame95( hdc
, &rect
, TRUE
, active
);
1686 else if (wndPtr
->dwStyle
& WS_THICKFRAME
)
1687 NC_DrawFrame95(hdc
, &rect
, FALSE
, active
);
1689 if ((wndPtr
->dwStyle
& WS_CAPTION
) == WS_CAPTION
)
1692 if (wndPtr
->dwExStyle
& WS_EX_TOOLWINDOW
) {
1693 r
.bottom
= rect
.top
+ sysMetrics
[SM_CYSMCAPTION
];
1694 rect
.top
+= sysMetrics
[SM_CYSMCAPTION
];
1697 r
.bottom
= rect
.top
+ sysMetrics
[SM_CYCAPTION
];
1698 rect
.top
+= sysMetrics
[SM_CYCAPTION
];
1700 NC_DrawCaption95 (hdc
, &r
, hwnd
, wndPtr
->dwStyle
,
1701 wndPtr
->dwExStyle
, active
);
1705 if (HAS_MENU(wndPtr
))
1708 r
.bottom
= rect
.top
+ sysMetrics
[SM_CYMENU
];
1710 TRACE(nonclient
, "Calling DrawMenuBar with "
1711 "rect (%d, %d)-(%d, %d)\n", r
.left
, r
.top
,
1714 rect
.top
+= MENU_DrawMenuBar( hdc
, &r
, hwnd
, suppress_menupaint
) + 1;
1717 TRACE(nonclient
, "After MenuBar, rect is (%d, %d)-(%d, %d).\n",
1718 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
1720 if (wndPtr
->dwExStyle
& WS_EX_CLIENTEDGE
)
1721 DrawEdge32 (hdc
, &rect
, EDGE_SUNKEN
, BF_RECT
| BF_ADJUST
);
1723 if (wndPtr
->dwExStyle
& WS_EX_STATICEDGE
)
1724 DrawEdge32 (hdc
, &rect
, BDR_SUNKENOUTER
, BF_RECT
| BF_ADJUST
);
1726 /* Draw the scroll-bars */
1728 if (wndPtr
->dwStyle
& WS_VSCROLL
)
1729 SCROLL_DrawScrollBar( hwnd
, hdc
, SB_VERT
, TRUE
, TRUE
);
1730 if (wndPtr
->dwStyle
& WS_HSCROLL
)
1731 SCROLL_DrawScrollBar( hwnd
, hdc
, SB_HORZ
, TRUE
, TRUE
);
1733 /* Draw the "size-box" */
1734 if ((wndPtr
->dwStyle
& WS_VSCROLL
) && (wndPtr
->dwStyle
& WS_HSCROLL
))
1737 r
.left
= r
.right
- SYSMETRICS_CXVSCROLL
+ 1;
1738 r
.top
= r
.bottom
- SYSMETRICS_CYHSCROLL
+ 1;
1739 FillRect32( hdc
, &r
, GetSysColorBrush32(COLOR_SCROLLBAR
) );
1742 ReleaseDC32( hwnd
, hdc
);
1748 /***********************************************************************
1751 * Handle a WM_NCPAINT message. Called from DefWindowProc().
1753 LONG
NC_HandleNCPaint( HWND32 hwnd
, HRGN32 clip
)
1755 WND
* wndPtr
= WIN_FindWndPtr( hwnd
);
1757 if( wndPtr
&& wndPtr
->dwStyle
& WS_VISIBLE
)
1759 if( wndPtr
->dwStyle
& WS_MINIMIZE
)
1760 WINPOS_RedrawIconTitle( hwnd
);
1761 else if (TWEAK_WineLook
== WIN31_LOOK
)
1762 NC_DoNCPaint( wndPtr
, clip
, FALSE
);
1764 NC_DoNCPaint95( wndPtr
, clip
, FALSE
);
1770 /***********************************************************************
1771 * NC_HandleNCActivate
1773 * Handle a WM_NCACTIVATE message. Called from DefWindowProc().
1775 LONG
NC_HandleNCActivate( WND
*wndPtr
, WPARAM16 wParam
)
1779 if( wParam
) wStateChange
= !(wndPtr
->flags
& WIN_NCACTIVATED
);
1780 else wStateChange
= wndPtr
->flags
& WIN_NCACTIVATED
;
1784 if (wParam
) wndPtr
->flags
|= WIN_NCACTIVATED
;
1785 else wndPtr
->flags
&= ~WIN_NCACTIVATED
;
1787 if( wndPtr
->dwStyle
& WS_MINIMIZE
)
1788 WINPOS_RedrawIconTitle( wndPtr
->hwndSelf
);
1789 else if (TWEAK_WineLook
== WIN31_LOOK
)
1790 NC_DoNCPaint( wndPtr
, (HRGN32
)1, FALSE
);
1792 NC_DoNCPaint95( wndPtr
, (HRGN32
)1, FALSE
);
1798 /***********************************************************************
1799 * NC_HandleSetCursor
1801 * Handle a WM_SETCURSOR message. Called from DefWindowProc().
1803 LONG
NC_HandleSetCursor( HWND32 hwnd
, WPARAM16 wParam
, LPARAM lParam
)
1805 if (hwnd
!= (HWND32
)wParam
) return 0; /* Don't set the cursor for child windows */
1807 switch(LOWORD(lParam
))
1811 WORD msg
= HIWORD( lParam
);
1812 if ((msg
== WM_LBUTTONDOWN
) || (msg
== WM_MBUTTONDOWN
) ||
1813 (msg
== WM_RBUTTONDOWN
))
1821 if (!(wndPtr
= WIN_FindWndPtr( hwnd
))) break;
1822 if (wndPtr
->class->hCursor
)
1824 SetCursor16( wndPtr
->class->hCursor
);
1832 return (LONG
)SetCursor16( LoadCursor16( 0, IDC_SIZEWE16
) );
1836 return (LONG
)SetCursor16( LoadCursor16( 0, IDC_SIZENS16
) );
1840 return (LONG
)SetCursor16( LoadCursor16( 0, IDC_SIZENWSE16
) );
1844 return (LONG
)SetCursor16( LoadCursor16( 0, IDC_SIZENESW16
) );
1847 /* Default cursor: arrow */
1848 return (LONG
)SetCursor16( LoadCursor16( 0, IDC_ARROW16
) );
1851 /***********************************************************************
1854 BOOL32
NC_GetSysPopupPos( WND
* wndPtr
, RECT32
* rect
)
1856 if( wndPtr
->hSysMenu
)
1858 if( wndPtr
->dwStyle
& WS_MINIMIZE
)
1859 GetWindowRect32( wndPtr
->hwndSelf
, rect
);
1862 if (TWEAK_WineLook
== WIN31_LOOK
)
1863 NC_GetInsideRect( wndPtr
->hwndSelf
, rect
);
1865 NC_GetInsideRect95( wndPtr
->hwndSelf
, rect
);
1866 OffsetRect32( rect
, wndPtr
->rectWindow
.left
, wndPtr
->rectWindow
.top
);
1867 if (wndPtr
->dwStyle
& WS_CHILD
)
1868 ClientToScreen32( wndPtr
->parent
->hwndSelf
, (POINT32
*)rect
);
1869 if (TWEAK_WineLook
== WIN31_LOOK
) {
1870 rect
->right
= rect
->left
+ SYSMETRICS_CXSIZE
;
1871 rect
->bottom
= rect
->top
+ SYSMETRICS_CYSIZE
;
1874 rect
->right
= rect
->left
+ sysMetrics
[SM_CYCAPTION
] - 1;
1875 rect
->bottom
= rect
->top
+ sysMetrics
[SM_CYCAPTION
] - 1;
1883 /***********************************************************************
1886 * Initialisation of a move or resize, when initiatied from a menu choice.
1887 * Return hit test code for caption or sizing border.
1889 static LONG
NC_StartSizeMove( WND
* wndPtr
, WPARAM16 wParam
,
1890 POINT16
*capturePoint
)
1896 if ((wParam
& 0xfff0) == SC_MOVE
)
1898 /* Move pointer at the center of the caption */
1900 if (TWEAK_WineLook
== WIN31_LOOK
)
1901 NC_GetInsideRect( wndPtr
->hwndSelf
, &rect
);
1903 NC_GetInsideRect95( wndPtr
->hwndSelf
, &rect
);
1904 if (wndPtr
->dwStyle
& WS_SYSMENU
)
1905 rect
.left
+= SYSMETRICS_CXSIZE
+ 1;
1906 if (wndPtr
->dwStyle
& WS_MINIMIZEBOX
)
1907 rect
.right
-= SYSMETRICS_CXSIZE
+ 1;
1908 if (wndPtr
->dwStyle
& WS_MAXIMIZEBOX
)
1909 rect
.right
-= SYSMETRICS_CXSIZE
+ 1;
1910 pt
.x
= wndPtr
->rectWindow
.left
+ (rect
.right
- rect
.left
) / 2;
1911 pt
.y
= wndPtr
->rectWindow
.top
+ rect
.top
+ SYSMETRICS_CYSIZE
/2;
1912 hittest
= HTCAPTION
;
1919 MSG_InternalGetMessage( &msg
, 0, 0, MSGF_SIZE
, PM_REMOVE
, FALSE
);
1923 hittest
= NC_HandleNCHitTest( wndPtr
->hwndSelf
, msg
.pt
);
1925 if ((hittest
< HTLEFT
) || (hittest
> HTBOTTOMRIGHT
))
1937 pt
.x
=(wndPtr
->rectWindow
.left
+wndPtr
->rectWindow
.right
)/2;
1938 pt
.y
= wndPtr
->rectWindow
.top
+ SYSMETRICS_CYFRAME
/ 2;
1942 pt
.x
=(wndPtr
->rectWindow
.left
+wndPtr
->rectWindow
.right
)/2;
1943 pt
.y
= wndPtr
->rectWindow
.bottom
- SYSMETRICS_CYFRAME
/ 2;
1947 pt
.x
= wndPtr
->rectWindow
.left
+ SYSMETRICS_CXFRAME
/ 2;
1948 pt
.y
=(wndPtr
->rectWindow
.top
+wndPtr
->rectWindow
.bottom
)/2;
1952 pt
.x
= wndPtr
->rectWindow
.right
- SYSMETRICS_CXFRAME
/ 2;
1953 pt
.y
=(wndPtr
->rectWindow
.top
+wndPtr
->rectWindow
.bottom
)/2;
1956 case VK_ESCAPE
: return 0;
1962 SetCursorPos32( pt
.x
, pt
.y
);
1963 NC_HandleSetCursor( wndPtr
->hwndSelf
,
1964 wndPtr
->hwndSelf
, MAKELONG( hittest
, WM_MOUSEMOVE
));
1969 /***********************************************************************
1972 * Perform SC_MOVE and SC_SIZE commands.
1974 static void NC_DoSizeMove( HWND32 hwnd
, WORD wParam
)
1977 RECT32 sizingRect
, mouseRect
;
1979 LONG hittest
= (LONG
)(wParam
& 0x0f);
1980 HCURSOR16 hDragCursor
= 0, hOldCursor
= 0;
1981 POINT32 minTrack
, maxTrack
;
1982 POINT16 capturePoint
, pt
;
1983 WND
* wndPtr
= WIN_FindWndPtr( hwnd
);
1984 BOOL32 thickframe
= HAS_THICKFRAME( wndPtr
->dwStyle
);
1985 BOOL32 iconic
= wndPtr
->dwStyle
& WS_MINIMIZE
;
1986 BOOL32 moved
= FALSE
;
1987 DWORD dwPoint
= GetMessagePos ();
1989 capturePoint
= pt
= *(POINT16
*)&dwPoint
;
1991 if (IsZoomed32(hwnd
) || !IsWindowVisible32(hwnd
) ||
1992 (wndPtr
->flags
& WIN_MANAGED
)) return;
1994 if ((wParam
& 0xfff0) == SC_MOVE
)
1996 if (!(wndPtr
->dwStyle
& WS_CAPTION
)) return;
1998 hittest
= NC_StartSizeMove( wndPtr
, wParam
, &capturePoint
);
1999 if (!hittest
) return;
2003 if (!thickframe
) return;
2004 if ( hittest
&& hittest
!= HTSYSMENU
) hittest
+= 2;
2008 hittest
= NC_StartSizeMove( wndPtr
, wParam
, &capturePoint
);
2017 /* Get min/max info */
2019 WINPOS_GetMinMaxInfo( wndPtr
, NULL
, NULL
, &minTrack
, &maxTrack
);
2020 sizingRect
= wndPtr
->rectWindow
;
2021 if (wndPtr
->dwStyle
& WS_CHILD
)
2022 GetClientRect32( wndPtr
->parent
->hwndSelf
, &mouseRect
);
2024 SetRect32(&mouseRect
, 0, 0, SYSMETRICS_CXSCREEN
, SYSMETRICS_CYSCREEN
);
2025 if (ON_LEFT_BORDER(hittest
))
2027 mouseRect
.left
= MAX( mouseRect
.left
, sizingRect
.right
-maxTrack
.x
);
2028 mouseRect
.right
= MIN( mouseRect
.right
, sizingRect
.right
-minTrack
.x
);
2030 else if (ON_RIGHT_BORDER(hittest
))
2032 mouseRect
.left
= MAX( mouseRect
.left
, sizingRect
.left
+minTrack
.x
);
2033 mouseRect
.right
= MIN( mouseRect
.right
, sizingRect
.left
+maxTrack
.x
);
2035 if (ON_TOP_BORDER(hittest
))
2037 mouseRect
.top
= MAX( mouseRect
.top
, sizingRect
.bottom
-maxTrack
.y
);
2038 mouseRect
.bottom
= MIN( mouseRect
.bottom
,sizingRect
.bottom
-minTrack
.y
);
2040 else if (ON_BOTTOM_BORDER(hittest
))
2042 mouseRect
.top
= MAX( mouseRect
.top
, sizingRect
.top
+minTrack
.y
);
2043 mouseRect
.bottom
= MIN( mouseRect
.bottom
, sizingRect
.top
+maxTrack
.y
);
2045 if (wndPtr
->dwStyle
& WS_CHILD
)
2047 MapWindowPoints32( wndPtr
->parent
->hwndSelf
, 0,
2048 (LPPOINT32
)&mouseRect
, 2 );
2050 SendMessage16( hwnd
, WM_ENTERSIZEMOVE
, 0, 0 );
2052 if (GetCapture32() != hwnd
) SetCapture32( hwnd
);
2054 if (wndPtr
->dwStyle
& WS_CHILD
)
2056 /* Retrieve a default cache DC (without using the window style) */
2057 hdc
= GetDCEx32( wndPtr
->parent
->hwndSelf
, 0, DCX_CACHE
);
2060 { /* Grab the server only when moving top-level windows without desktop */
2064 wndPtr
->pDriver
->pPreSizeMove(wndPtr
);
2066 if( iconic
) /* create a cursor for dragging */
2068 HICON16 hIcon
= (wndPtr
->class->hIcon
) ? wndPtr
->class->hIcon
2069 : (HICON16
)SendMessage16( hwnd
, WM_QUERYDRAGICON
, 0, 0L);
2070 if( hIcon
) hDragCursor
= CURSORICON_IconToCursor( hIcon
, TRUE
);
2071 if( !hDragCursor
) iconic
= FALSE
;
2074 if( !iconic
) NC_DrawMovingFrame( hdc
, &sizingRect
, thickframe
);
2080 MSG_InternalGetMessage( &msg
, 0, 0, MSGF_SIZE
, PM_REMOVE
, FALSE
);
2082 /* Exit on button-up, Return, or Esc */
2083 if ((msg
.message
== WM_LBUTTONUP
) ||
2084 ((msg
.message
== WM_KEYDOWN
) &&
2085 ((msg
.wParam
== VK_RETURN
) || (msg
.wParam
== VK_ESCAPE
)))) break;
2087 if ((msg
.message
!= WM_KEYDOWN
) && (msg
.message
!= WM_MOUSEMOVE
))
2088 continue; /* We are not interested in other messages */
2090 dwPoint
= GetMessagePos ();
2091 pt
= *(POINT16
*)&dwPoint
;
2093 if (msg
.message
== WM_KEYDOWN
) switch(msg
.wParam
)
2095 case VK_UP
: pt
.y
-= 8; break;
2096 case VK_DOWN
: pt
.y
+= 8; break;
2097 case VK_LEFT
: pt
.x
-= 8; break;
2098 case VK_RIGHT
: pt
.x
+= 8; break;
2101 pt
.x
= MAX( pt
.x
, mouseRect
.left
);
2102 pt
.x
= MIN( pt
.x
, mouseRect
.right
);
2103 pt
.y
= MAX( pt
.y
, mouseRect
.top
);
2104 pt
.y
= MIN( pt
.y
, mouseRect
.bottom
);
2106 dx
= pt
.x
- capturePoint
.x
;
2107 dy
= pt
.y
- capturePoint
.y
;
2114 if( iconic
) /* ok, no system popup tracking */
2116 hOldCursor
= SetCursor32(hDragCursor
);
2117 ShowCursor32( TRUE
);
2118 WINPOS_ShowIconTitle( wndPtr
, FALSE
);
2122 if (msg
.message
== WM_KEYDOWN
) SetCursorPos32( pt
.x
, pt
.y
);
2125 RECT32 newRect
= sizingRect
;
2127 if (hittest
== HTCAPTION
) OffsetRect32( &newRect
, dx
, dy
);
2128 if (ON_LEFT_BORDER(hittest
)) newRect
.left
+= dx
;
2129 else if (ON_RIGHT_BORDER(hittest
)) newRect
.right
+= dx
;
2130 if (ON_TOP_BORDER(hittest
)) newRect
.top
+= dy
;
2131 else if (ON_BOTTOM_BORDER(hittest
)) newRect
.bottom
+= dy
;
2134 NC_DrawMovingFrame( hdc
, &sizingRect
, thickframe
);
2135 NC_DrawMovingFrame( hdc
, &newRect
, thickframe
);
2138 sizingRect
= newRect
;
2146 if( moved
) /* restore cursors, show icon title later on */
2148 ShowCursor32( FALSE
);
2149 SetCursor32( hOldCursor
);
2151 DestroyCursor32( hDragCursor
);
2154 NC_DrawMovingFrame( hdc
, &sizingRect
, thickframe
);
2156 if (wndPtr
->dwStyle
& WS_CHILD
)
2157 ReleaseDC32( wndPtr
->parent
->hwndSelf
, hdc
);
2160 ReleaseDC32( 0, hdc
);
2163 wndPtr
->pDriver
->pPostSizeMove(wndPtr
);
2165 if (HOOK_IsHooked( WH_CBT
))
2167 RECT16
* pr
= SEGPTR_NEW(RECT16
);
2170 CONV_RECT32TO16( &sizingRect
, pr
);
2171 if( HOOK_CallHooks16( WH_CBT
, HCBT_MOVESIZE
, hwnd
,
2172 (LPARAM
)SEGPTR_GET(pr
)) )
2173 sizingRect
= wndPtr
->rectWindow
;
2175 CONV_RECT16TO32( pr
, &sizingRect
);
2179 SendMessage16( hwnd
, WM_EXITSIZEMOVE
, 0, 0 );
2180 SendMessage16( hwnd
, WM_SETVISIBLE
, !IsIconic16(hwnd
), 0L);
2182 if( moved
&& !((msg
.message
== WM_KEYDOWN
) && (msg
.wParam
== VK_ESCAPE
)) )
2184 /* NOTE: SWP_NOACTIVATE prevents document window activation in Word 6 */
2185 SetWindowPos32( hwnd
, 0, sizingRect
.left
, sizingRect
.top
,
2186 sizingRect
.right
- sizingRect
.left
,
2187 sizingRect
.bottom
- sizingRect
.top
,
2188 ( hittest
== HTCAPTION
) ? SWP_NOSIZE
: 0 );
2191 if( IsWindow32(hwnd
) )
2192 if( wndPtr
->dwStyle
& WS_MINIMIZE
)
2194 /* Single click brings up the system menu when iconized */
2198 if( wndPtr
->dwStyle
& WS_SYSMENU
)
2199 SendMessage16( hwnd
, WM_SYSCOMMAND
,
2200 SC_MOUSEMENU
+ HTSYSMENU
, *((LPARAM
*)&pt
));
2202 else WINPOS_ShowIconTitle( wndPtr
, TRUE
);
2207 /***********************************************************************
2210 * Track a mouse button press on the minimize or maximize box.
2212 static void NC_TrackMinMaxBox( HWND32 hwnd
, WORD wParam
)
2215 HDC32 hdc
= GetWindowDC32( hwnd
);
2216 BOOL32 pressed
= TRUE
;
2217 void (*paintButton
)(HWND32
, HDC16
, BOOL32
);
2219 SetCapture32( hwnd
);
2220 if (wParam
== HTMINBUTTON
)
2222 (TWEAK_WineLook
== WIN31_LOOK
) ? &NC_DrawMinButton
: &NC_DrawMinButton95
;
2225 (TWEAK_WineLook
== WIN31_LOOK
) ? &NC_DrawMaxButton
: &NC_DrawMaxButton95
;
2227 (*paintButton
)( hwnd
, hdc
, TRUE
);
2231 BOOL32 oldstate
= pressed
;
2232 MSG_InternalGetMessage( &msg
, 0, 0, 0, PM_REMOVE
, FALSE
);
2234 pressed
= (NC_HandleNCHitTest( hwnd
, msg
.pt
) == wParam
);
2235 if (pressed
!= oldstate
)
2236 (*paintButton
)( hwnd
, hdc
, pressed
);
2237 } while (msg
.message
!= WM_LBUTTONUP
);
2239 (*paintButton
)( hwnd
, hdc
, FALSE
);
2242 ReleaseDC32( hwnd
, hdc
);
2243 if (!pressed
) return;
2245 if (wParam
== HTMINBUTTON
)
2246 SendMessage16( hwnd
, WM_SYSCOMMAND
, SC_MINIMIZE
, *(LONG
*)&msg
.pt
);
2248 SendMessage16( hwnd
, WM_SYSCOMMAND
,
2249 IsZoomed32(hwnd
) ? SC_RESTORE
:SC_MAXIMIZE
, *(LONG
*)&msg
.pt
);
2253 /***********************************************************************
2254 * NC_TrackCloseButton95
2256 * Track a mouse button press on the Win95 close button.
2259 NC_TrackCloseButton95 (HWND32 hwnd
, WORD wParam
)
2262 HDC32 hdc
= GetWindowDC32( hwnd
);
2263 BOOL32 pressed
= TRUE
;
2265 SetCapture32( hwnd
);
2267 NC_DrawCloseButton95 (hwnd
, hdc
, TRUE
);
2271 BOOL32 oldstate
= pressed
;
2272 MSG_InternalGetMessage( &msg
, 0, 0, 0, PM_REMOVE
, FALSE
);
2274 pressed
= (NC_HandleNCHitTest( hwnd
, msg
.pt
) == wParam
);
2275 if (pressed
!= oldstate
)
2276 NC_DrawCloseButton95 (hwnd
, hdc
, pressed
);
2277 } while (msg
.message
!= WM_LBUTTONUP
);
2279 NC_DrawCloseButton95 (hwnd
, hdc
, FALSE
);
2282 ReleaseDC32( hwnd
, hdc
);
2283 if (!pressed
) return;
2285 SendMessage16( hwnd
, WM_SYSCOMMAND
, SC_CLOSE
, *(LONG
*)&msg
.pt
);
2289 /***********************************************************************
2292 * Track a mouse button press on the horizontal or vertical scroll-bar.
2294 static void NC_TrackScrollBar( HWND32 hwnd
, WPARAM32 wParam
, POINT32 pt
)
2298 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
2300 if ((wParam
& 0xfff0) == SC_HSCROLL
)
2302 if ((wParam
& 0x0f) != HTHSCROLL
) return;
2303 scrollbar
= SB_HORZ
;
2305 else /* SC_VSCROLL */
2307 if ((wParam
& 0x0f) != HTVSCROLL
) return;
2308 scrollbar
= SB_VERT
;
2311 if (!(msg
= SEGPTR_NEW(MSG16
))) return;
2312 pt
.x
-= wndPtr
->rectWindow
.left
;
2313 pt
.y
-= wndPtr
->rectWindow
.top
;
2314 SetCapture32( hwnd
);
2315 SCROLL_HandleScrollEvent( hwnd
, scrollbar
, WM_LBUTTONDOWN
, pt
);
2319 GetMessage16( SEGPTR_GET(msg
), 0, 0, 0 );
2320 switch(msg
->message
)
2325 pt
.x
= LOWORD(msg
->lParam
) + wndPtr
->rectClient
.left
-
2326 wndPtr
->rectWindow
.left
;
2327 pt
.y
= HIWORD(msg
->lParam
) + wndPtr
->rectClient
.top
-
2328 wndPtr
->rectWindow
.top
;
2329 SCROLL_HandleScrollEvent( hwnd
, scrollbar
, msg
->message
, pt
);
2332 TranslateMessage16( msg
);
2333 DispatchMessage16( msg
);
2336 if (!IsWindow32( hwnd
))
2341 } while (msg
->message
!= WM_LBUTTONUP
);
2345 /***********************************************************************
2346 * NC_HandleNCLButtonDown
2348 * Handle a WM_NCLBUTTONDOWN message. Called from DefWindowProc().
2350 LONG
NC_HandleNCLButtonDown( WND
* pWnd
, WPARAM16 wParam
, LPARAM lParam
)
2352 HWND32 hwnd
= pWnd
->hwndSelf
;
2354 switch(wParam
) /* Hit test */
2357 hwnd
= WIN_GetTopParent(hwnd
);
2359 if( WINPOS_SetActiveWindow(hwnd
, TRUE
, TRUE
) || (GetActiveWindow32() == hwnd
) )
2360 SendMessage16( pWnd
->hwndSelf
, WM_SYSCOMMAND
, SC_MOVE
+ HTCAPTION
, lParam
);
2364 if( pWnd
->dwStyle
& WS_SYSMENU
)
2366 if( !(pWnd
->dwStyle
& WS_MINIMIZE
) )
2368 HDC32 hDC
= GetWindowDC32(hwnd
);
2369 if (TWEAK_WineLook
== WIN31_LOOK
)
2370 NC_DrawSysButton( hwnd
, hDC
, TRUE
);
2372 NC_DrawSysButton95( hwnd
, hDC
, TRUE
);
2373 ReleaseDC32( hwnd
, hDC
);
2375 SendMessage16( hwnd
, WM_SYSCOMMAND
, SC_MOUSEMENU
+ HTSYSMENU
, lParam
);
2380 SendMessage16( hwnd
, WM_SYSCOMMAND
, SC_MOUSEMENU
, lParam
);
2384 SendMessage16( hwnd
, WM_SYSCOMMAND
, SC_HSCROLL
+ HTHSCROLL
, lParam
);
2388 SendMessage16( hwnd
, WM_SYSCOMMAND
, SC_VSCROLL
+ HTVSCROLL
, lParam
);
2393 NC_TrackMinMaxBox( hwnd
, wParam
);
2397 if (TWEAK_WineLook
>= WIN95_LOOK
)
2398 NC_TrackCloseButton95 (hwnd
, wParam
);
2409 /* make sure hittest fits into 0xf and doesn't overlap with HTSYSMENU */
2410 SendMessage16( hwnd
, WM_SYSCOMMAND
, SC_SIZE
+ wParam
- 2, lParam
);
2420 /***********************************************************************
2421 * NC_HandleNCLButtonDblClk
2423 * Handle a WM_NCLBUTTONDBLCLK message. Called from DefWindowProc().
2425 LONG
NC_HandleNCLButtonDblClk( WND
*pWnd
, WPARAM16 wParam
, LPARAM lParam
)
2428 * if this is an icon, send a restore since we are handling
2431 if (pWnd
->dwStyle
& WS_MINIMIZE
)
2433 SendMessage16( pWnd
->hwndSelf
, WM_SYSCOMMAND
, SC_RESTORE
, lParam
);
2437 switch(wParam
) /* Hit test */
2440 /* stop processing if WS_MAXIMIZEBOX is missing */
2441 if (pWnd
->dwStyle
& WS_MAXIMIZEBOX
)
2442 SendMessage16( pWnd
->hwndSelf
, WM_SYSCOMMAND
,
2443 (pWnd
->dwStyle
& WS_MAXIMIZE
) ? SC_RESTORE
: SC_MAXIMIZE
,
2448 if (!(pWnd
->class->style
& CS_NOCLOSE
))
2449 SendMessage16( pWnd
->hwndSelf
, WM_SYSCOMMAND
, SC_CLOSE
, lParam
);
2453 SendMessage16( pWnd
->hwndSelf
, WM_SYSCOMMAND
, SC_HSCROLL
+ HTHSCROLL
,
2458 SendMessage16( pWnd
->hwndSelf
, WM_SYSCOMMAND
, SC_VSCROLL
+ HTVSCROLL
,
2466 /***********************************************************************
2467 * NC_HandleSysCommand
2469 * Handle a WM_SYSCOMMAND message. Called from DefWindowProc().
2471 LONG
NC_HandleSysCommand( HWND32 hwnd
, WPARAM16 wParam
, POINT16 pt
)
2473 WND
*wndPtr
= WIN_FindWndPtr( hwnd
);
2475 UINT16 uCommand
= wParam
& 0xFFF0;
2477 TRACE(nonclient
, "Handling WM_SYSCOMMAND %x %d,%d\n",
2478 wParam
, pt
.x
, pt
.y
);
2480 if (wndPtr
->dwStyle
& WS_CHILD
&& uCommand
!= SC_KEYMENU
)
2481 ScreenToClient16( wndPtr
->parent
->hwndSelf
, &pt
);
2487 NC_DoSizeMove( hwnd
, wParam
);
2491 ShowWindow32( hwnd
, SW_MINIMIZE
);
2495 ShowWindow32( hwnd
, SW_MAXIMIZE
);
2499 ShowWindow32( hwnd
, SW_RESTORE
);
2503 return SendMessage16( hwnd
, WM_CLOSE
, 0, 0 );
2507 CONV_POINT16TO32( &pt
, &pt32
);
2508 NC_TrackScrollBar( hwnd
, wParam
, pt32
);
2512 CONV_POINT16TO32( &pt
, &pt32
);
2513 MENU_TrackMouseMenuBar( wndPtr
, wParam
& 0x000F, pt32
);
2517 MENU_TrackKbdMenuBar( wndPtr
, wParam
, pt
.x
);
2521 WinExec32( "taskman.exe", SW_SHOWNORMAL
);
2525 if (wParam
== SC_ABOUTWINE
)
2526 ShellAbout32A(hwnd
,"Wine", WINE_RELEASE_INFO
, 0);
2528 if (wParam
== SC_PUTMARK
)
2529 TRACE(shell
,"Mark requested by user\n");
2536 FIXME (nonclient
, "unimplemented!\n");