467ca076c52e6044c340ba138b23def0f8508576
[reactos.git] / reactos / dll / win32 / user32 / controls / icontitle.c
1 /*
2 * Icontitle window class.
3 *
4 * Copyright 1997 Alex Korobka
5 *
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19 */
20
21 #include <user32.h>
22
23 #include <wine/debug.h>
24
25 static BOOL bMultiLineTitle;
26 static HFONT hIconTitleFont;
27
28 /*********************************************************************
29 * icon title class descriptor
30 */
31 const struct builtin_class_descr ICONTITLE_builtin_class =
32 {
33 WC_ICONTITLE, /* name */
34 0, /* style */
35 NULL, /* procA (winproc is Unicode only) */
36 IconTitleWndProc, /* procW */
37 0, /* extra */
38 IDC_ARROW, /* cursor */
39 0 /* brush */
40 };
41
42
43
44 #ifndef __REACTOS__
45 /***********************************************************************
46 * ICONTITLE_Create
47 */
48 HWND ICONTITLE_Create( HWND owner )
49 {
50 HWND hWnd;
51 HINSTANCE instance = (HINSTANCE)GetWindowLongPtrA( owner, GWLP_HINSTANCE );
52 LONG style = WS_CLIPSIBLINGS;
53
54 if (!IsWindowEnabled(owner)) style |= WS_DISABLED;
55 if( GetWindowLongPtrA( owner, GWL_STYLE ) & WS_CHILD )
56 hWnd = CreateWindowExA( 0, (LPCSTR)ICONTITLE_CLASS_ATOM, NULL,
57 style | WS_CHILD, 0, 0, 1, 1,
58 GetParent(owner), 0, instance, NULL );
59 else
60 hWnd = CreateWindowExA( 0, (LPCSTR)ICONTITLE_CLASS_ATOM, NULL,
61 style, 0, 0, 1, 1,
62 owner, 0, instance, NULL );
63 WIN_SetOwner( hWnd, owner ); /* MDI depends on this */
64 SetWindowLongPtrW( hWnd, GWL_STYLE,
65 GetWindowLongPtrW( hWnd, GWL_STYLE ) & ~(WS_CAPTION | WS_BORDER) );
66 return hWnd;
67 }
68 #endif
69
70 /***********************************************************************
71 * ICONTITLE_SetTitlePos
72 */
73 static BOOL ICONTITLE_SetTitlePos( HWND hwnd, HWND owner )
74 {
75 static const WCHAR emptyTitleText[] = {'<','.','.','.','>',0};
76 WCHAR str[80];
77 HDC hDC;
78 HFONT hPrevFont;
79 RECT rect;
80 INT cx, cy;
81 POINT pt;
82
83 int length = GetWindowTextW( owner, str, sizeof(str)/sizeof(WCHAR) );
84
85 while (length && str[length - 1] == ' ') /* remove trailing spaces */
86 str[--length] = 0;
87
88 if( !length )
89 {
90 strcpyW( str, emptyTitleText );
91 length = strlenW( str );
92 }
93
94 if (!(hDC = GetDC( hwnd ))) return FALSE;
95
96 hPrevFont = SelectObject( hDC, hIconTitleFont );
97
98 SetRect( &rect, 0, 0, GetSystemMetrics(SM_CXICONSPACING) -
99 GetSystemMetrics(SM_CXBORDER) * 2,
100 GetSystemMetrics(SM_CYBORDER) * 2 );
101
102 DrawTextW( hDC, str, length, &rect, DT_CALCRECT | DT_CENTER | DT_NOPREFIX | DT_WORDBREAK |
103 (( bMultiLineTitle ) ? 0 : DT_SINGLELINE) );
104
105 SelectObject( hDC, hPrevFont );
106 ReleaseDC( hwnd, hDC );
107
108 cx = rect.right - rect.left + 4 * GetSystemMetrics(SM_CXBORDER);
109 cy = rect.bottom - rect.top;
110
111 pt.x = (GetSystemMetrics(SM_CXICON) - cx) / 2;
112 pt.y = GetSystemMetrics(SM_CYICON);
113
114 /* point is relative to owner, make it relative to parent */
115 MapWindowPoints( owner, GetParent(hwnd), &pt, 1 );
116
117 SetWindowPos( hwnd, owner, pt.x, pt.y, cx, cy, SWP_NOACTIVATE );
118 return TRUE;
119 }
120
121 /***********************************************************************
122 * ICONTITLE_Paint
123 */
124 static BOOL ICONTITLE_Paint( HWND hwnd, HWND owner, HDC hDC, BOOL bActive )
125 {
126 RECT rect;
127 HFONT hPrevFont;
128 HBRUSH hBrush = 0;
129 COLORREF textColor = 0;
130
131 if( bActive )
132 {
133 hBrush = GetSysColorBrush(COLOR_ACTIVECAPTION);
134 textColor = GetSysColor(COLOR_CAPTIONTEXT);
135 }
136 else
137 {
138 if( GetWindowLongPtrA( hwnd, GWL_STYLE ) & WS_CHILD )
139 {
140 hBrush = (HBRUSH) GetClassLongPtrW(hwnd, GCLP_HBRBACKGROUND);
141 if( hBrush )
142 {
143 INT level;
144 LOGBRUSH logBrush;
145 GetObjectA( hBrush, sizeof(logBrush), &logBrush );
146 level = GetRValue(logBrush.lbColor) +
147 GetGValue(logBrush.lbColor) +
148 GetBValue(logBrush.lbColor);
149 if( level < (0x7F * 3) )
150 textColor = RGB( 0xFF, 0xFF, 0xFF );
151 }
152 else
153 hBrush = GetStockObject( WHITE_BRUSH );
154 }
155 else
156 {
157 hBrush = GetStockObject( BLACK_BRUSH );
158 textColor = RGB( 0xFF, 0xFF, 0xFF );
159 }
160 }
161
162 GetClientRect( hwnd, &rect );
163 DPtoLP( hDC, (LPPOINT)&rect, 2 );
164 FillRect( hDC, &rect, hBrush );
165
166 hPrevFont = SelectObject( hDC, hIconTitleFont );
167 if( hPrevFont )
168 {
169 WCHAR buffer[80];
170
171 INT length = GetWindowTextW( owner, buffer, sizeof(buffer)/sizeof(buffer[0]) );
172 SetTextColor( hDC, textColor );
173 SetBkMode( hDC, TRANSPARENT );
174
175 DrawTextW( hDC, buffer, length, &rect, DT_CENTER | DT_NOPREFIX |
176 DT_WORDBREAK | ((bMultiLineTitle) ? 0 : DT_SINGLELINE) );
177
178 SelectObject( hDC, hPrevFont );
179 }
180 return (hPrevFont != 0);
181 }
182
183 /***********************************************************************
184 * IconTitleWndProc
185 */
186 LRESULT WINAPI IconTitleWndProc( HWND hWnd, UINT msg,
187 WPARAM wParam, LPARAM lParam )
188 {
189 HWND owner = GetWindow( hWnd, GW_OWNER );
190
191 if (!IsWindow(hWnd)) return 0;
192
193 switch( msg )
194 {
195 case WM_CREATE:
196 if (!hIconTitleFont)
197 {
198 LOGFONTA logFont;
199 SystemParametersInfoA( SPI_GETICONTITLELOGFONT, 0, &logFont, 0 );
200 SystemParametersInfoA( SPI_GETICONTITLEWRAP, 0, &bMultiLineTitle, 0 );
201 hIconTitleFont = CreateFontIndirectA( &logFont );
202 }
203 return (hIconTitleFont ? 0 : -1);
204 case WM_NCHITTEST:
205 return HTCAPTION;
206 case WM_NCMOUSEMOVE:
207 case WM_NCLBUTTONDBLCLK:
208 return SendMessageW( owner, msg, wParam, lParam );
209 case WM_ACTIVATE:
210 if( wParam ) SetActiveWindow( owner );
211 return 0;
212 case WM_CLOSE:
213 return 0;
214 case WM_SHOWWINDOW:
215 if (wParam) ICONTITLE_SetTitlePos( hWnd, owner );
216 return 0;
217 case WM_ERASEBKGND:
218 if( GetWindowLongPtrW( owner, GWL_STYLE ) & WS_CHILD )
219 lParam = SendMessageW( owner, WM_ISACTIVEICON, 0, 0 );
220 else
221 lParam = (owner == GetActiveWindow());
222 if( ICONTITLE_Paint( hWnd, owner, (HDC)wParam, (BOOL)lParam ) )
223 ValidateRect( hWnd, NULL );
224 return 1;
225 }
226 return DefWindowProcW( hWnd, msg, wParam, lParam );
227 }