1 /* MS-Windows Engine (aka GTK-Wimp)
3 * Copyright (C) 2003, 2004 Raymond Penners <raymond@dotsphinx.com>
4 * Copyright (C) 2006 Hong Jen Yee (PCMan) <pcman.tw@gmail.com>
5 * Includes code adapted from redmond95 by Owen Taylor, and
6 * gtk-nativewin by Evan Martin
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Library General Public
10 * License as published by the Free Software Foundation; either
11 * version 2 of the License, or (at your option) any later version.
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Library General Public License for more details.
18 * You should have received a copy of the GNU Library General Public
19 * License along with this library. If not, see <http://www.gnu.org/licenses/>.
25 * http://lxr.mozilla.org/seamonkey/source/widget/src/windows/nsNativeThemeWin.cpp
26 * http://lxr.mozilla.org/seamonkey/source/widget/src/windows/nsLookAndFeel.cpp
27 * http://msdn.microsoft.com/library/default.asp?url=/library/en-us/shellcc/platform/commctls/userex/functions/drawthemebackground.asp
28 * http://msdn.microsoft.com/library/default.asp?url=/library/en-us/gdi/pantdraw_4b3g.asp
31 /* Include first, else we get redefinition warnings about STRICT */
32 #include "pango/pangowin32.h"
34 #include "msw_style.h"
44 #ifndef GTK_COMPILATION
45 #define GTK_COMPILATION
47 #include "gtk/gtkmenushellprivate.h"
49 #ifdef BUILDING_STANDALONE
50 #include "gdk/gdkwin32.h"
52 #include "gdk/win32/gdkwin32.h"
56 /* Default values, not normally used
58 static const GtkRequisition default_option_indicator_size = { 9, 8 };
59 static const GtkBorder default_option_indicator_spacing = { 7, 5, 2, 2 };
61 static GtkStyleClass *parent_class;
62 static HBRUSH g_dither_brush = NULL;
64 static HPEN g_light_pen = NULL;
65 static HPEN g_dark_pen = NULL;
87 static const unsigned char check_aa_bits[] = {
88 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
89 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
90 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
91 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
92 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
93 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
94 0x00, 0x00, 0x00, 0x00
96 static const unsigned char check_base_bits[] = {
97 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
98 0xfc, 0x07, 0x00, 0x00, 0xfc, 0x07, 0x00, 0x00,
99 0xfc, 0x07, 0x00, 0x00, 0xfc, 0x07, 0x00, 0x00,
100 0xfc, 0x07, 0x00, 0x00, 0xfc, 0x07, 0x00, 0x00,
101 0xfc, 0x07, 0x00, 0x00, 0xfc, 0x07, 0x00, 0x00,
102 0xfc, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
103 0x00, 0x00, 0x00, 0x00
105 static const unsigned char check_black_bits[] = {
106 0x00, 0x00, 0x00, 0x00, 0xfe, 0x0f, 0x00, 0x00,
107 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
108 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
109 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
110 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
111 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
112 0x00, 0x00, 0x00, 0x00
114 static const unsigned char check_dark_bits[] = {
115 0xff, 0x1f, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
116 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
117 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
118 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
119 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
120 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
121 0x01, 0x00, 0x00, 0x00
123 static const unsigned char check_light_bits[] = {
124 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00,
125 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00,
126 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00,
127 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00,
128 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00,
129 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00,
130 0xfe, 0x1f, 0x00, 0x00
132 static const unsigned char check_mid_bits[] = {
133 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
134 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00,
135 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00,
136 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00,
137 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00,
138 0x00, 0x08, 0x00, 0x00, 0xfc, 0x0f, 0x00, 0x00,
139 0x00, 0x00, 0x00, 0x00
141 static const unsigned char check_text_bits[] = {
142 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
143 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00,
144 0x00, 0x03, 0x00, 0x00, 0x88, 0x03, 0x00, 0x00,
145 0xd8, 0x01, 0x00, 0x00, 0xf8, 0x00, 0x00, 0x00,
146 0x70, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00,
147 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
148 0x00, 0x00, 0x00, 0x00
150 static const unsigned char check_inconsistent_bits[] = {
151 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
152 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
153 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
154 0xf0, 0x03, 0x00, 0x00, 0xf0, 0x03, 0x00, 0x00,
155 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
156 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
157 0x00, 0x00, 0x00, 0x00
159 static const unsigned char radio_base_bits[] = {
160 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
161 0xf0, 0x01, 0x00, 0x00, 0xf8, 0x03, 0x00, 0x00,
162 0xfc, 0x07, 0x00, 0x00, 0xfc, 0x07, 0x00, 0x00,
163 0xfc, 0x07, 0x00, 0x00, 0xfc, 0x07, 0x00, 0x00,
164 0xfc, 0x07, 0x00, 0x00, 0xf8, 0x03, 0x00, 0x00,
165 0xf0, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
166 0x00, 0x00, 0x00, 0x00
168 static const unsigned char radio_black_bits[] = {
169 0x00, 0x00, 0x00, 0x00, 0xf0, 0x01, 0x00, 0x00,
170 0x0c, 0x02, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
171 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
172 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
173 0x02, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
174 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
175 0x00, 0x00, 0x00, 0x00
177 static const unsigned char radio_dark_bits[] = {
178 0xf0, 0x01, 0x00, 0x00, 0x0c, 0x06, 0x00, 0x00,
179 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
180 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
181 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
182 0x01, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
183 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
184 0x00, 0x00, 0x00, 0x00
186 static const unsigned char radio_light_bits[] = {
187 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
188 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00,
189 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00,
190 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00,
191 0x00, 0x10, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00,
192 0x00, 0x08, 0x00, 0x00, 0x0c, 0x06, 0x00, 0x00,
193 0xf0, 0x01, 0x00, 0x00
195 static const unsigned char radio_mid_bits[] = {
196 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
197 0x00, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00,
198 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00,
199 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00,
200 0x00, 0x08, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00,
201 0x0c, 0x06, 0x00, 0x00, 0xf0, 0x01, 0x00, 0x00,
202 0x00, 0x00, 0x00, 0x00
204 static const unsigned char radio_text_bits[] = {
205 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
206 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
207 0xe0, 0x00, 0x00, 0x00, 0xf0, 0x01, 0x00, 0x00,
208 0xf0, 0x01, 0x00, 0x00, 0xf0, 0x01, 0x00, 0x00,
209 0xe0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
210 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
211 0x00, 0x00, 0x00, 0x00
216 const unsigned char *bits;
217 cairo_surface_t *bmap;
219 { check_aa_bits, NULL },
220 { check_base_bits, NULL },
221 { check_black_bits, NULL },
222 { check_dark_bits, NULL },
223 { check_light_bits, NULL },
224 { check_mid_bits, NULL },
225 { check_text_bits, NULL },
226 { check_inconsistent_bits, NULL },
227 { radio_base_bits, NULL },
228 { radio_black_bits, NULL },
229 { radio_dark_bits, NULL },
230 { radio_light_bits, NULL },
231 { radio_mid_bits, NULL },
232 { radio_text_bits, NULL }
236 _cairo_draw_line (cairo_t *cr,
245 gdk_cairo_set_source_color (cr, color);
246 cairo_set_line_cap (cr, CAIRO_LINE_CAP_SQUARE);
247 cairo_set_line_width (cr, 1.0);
249 cairo_move_to (cr, x1 + 0.5, y1 + 0.5);
250 cairo_line_to (cr, x2 + 0.5, y2 + 0.5);
257 _cairo_draw_rectangle (cairo_t *cr,
265 gdk_cairo_set_source_color (cr, color);
269 cairo_rectangle (cr, x, y, width, height);
274 cairo_rectangle (cr, x + 0.5, y + 0.5, width, height);
280 get_system_font (XpThemeClass klazz, XpThemeFont type, LOGFONTW *out_lf)
282 if (xp_theme_get_system_font (klazz, type, out_lf))
288 /* Use wide char versions here, as the theming functions only support
289 * wide chars versions of the structures. */
290 NONCLIENTMETRICSW ncm;
292 ncm.cbSize = sizeof (NONCLIENTMETRICSW);
294 if (SystemParametersInfoW (SPI_GETNONCLIENTMETRICS,
295 sizeof (NONCLIENTMETRICSW), &ncm, 0))
297 if (type == XP_THEME_FONT_CAPTION)
298 *out_lf = ncm.lfCaptionFont;
299 else if (type == XP_THEME_FONT_MENU)
300 *out_lf = ncm.lfMenuFont;
301 else if (type == XP_THEME_FONT_STATUS)
302 *out_lf = ncm.lfStatusFont;
304 *out_lf = ncm.lfMessageFont;
314 sys_font_to_pango_font (XpThemeClass klazz, XpThemeFont type, char *buf,
319 if (get_system_font (klazz, type, &lf))
321 PangoFontDescription *desc = NULL;
325 desc = pango_win32_font_description_from_logfontw (&lf);
329 font = pango_font_description_to_string (desc);
330 pt_size = pango_font_description_get_size (desc);
332 if (!(font && *font))
334 pango_font_description_free (desc);
343 hwnd = GetDesktopWindow ();
347 pt_size = -MulDiv (lf.lfHeight, 72, GetDeviceCaps (hDC, LOGPIXELSY));
352 ReleaseDC (hwnd, hDC);
354 g_snprintf (buf, bufsiz, "%s %d", font, pt_size);
358 g_snprintf (buf, bufsiz, "%s", font);
362 pango_font_description_free (desc);
370 /* missing from ms's header files */
371 #ifndef SPI_GETMENUSHOWDELAY
372 #define SPI_GETMENUSHOWDELAY 106
375 /* I don't know the proper XP theme class for things like
376 HIGHLIGHTTEXT, so we'll just define it to be "BUTTON"
378 #define XP_THEME_CLASS_TEXT XP_THEME_CLASS_BUTTON
380 #define WIN95_VERSION 0x400
381 #define WIN2K_VERSION 0x500
382 #define WINXP_VERSION 0x501
383 #define WIN2K3_VERSION 0x502
384 #define VISTA_VERSION 0x600
387 get_windows_version ()
389 static gint32 version = 0;
390 static gboolean have_version = FALSE;
394 OSVERSIONINFOEX osvi;
397 ZeroMemory (&osvi, sizeof (OSVERSIONINFOEX));
398 osvi.dwOSVersionInfoSize = sizeof (OSVERSIONINFOEX);
400 GetVersionEx((OSVERSIONINFO*) &osvi);
402 version = (osvi.dwMajorVersion & 0xff) << 8 | (osvi.dwMinorVersion & 0xff);
409 setup_menu_settings (GtkSettings *settings)
412 GObjectClass *klazz = G_OBJECT_GET_CLASS (G_OBJECT (settings));
414 if (get_windows_version () > WIN95_VERSION)
416 if (SystemParametersInfo (SPI_GETMENUSHOWDELAY, 0, &menu_delay, 0))
420 if (g_object_class_find_property
421 (klazz, "gtk-menu-bar-popup-delay"))
423 g_object_set (settings,
424 "gtk-menu-bar-popup-delay", 0, NULL);
426 if (g_object_class_find_property
427 (klazz, "gtk-menu-popup-delay"))
429 g_object_set (settings,
430 "gtk-menu-popup-delay", menu_delay, NULL);
432 if (g_object_class_find_property
433 (klazz, "gtk-menu-popdown-delay"))
435 g_object_set (settings,
436 "gtk-menu-popdown-delay", menu_delay, NULL);
444 msw_style_setup_system_settings (void)
446 GtkSettings *settings;
447 int cursor_blink_time;
449 settings = gtk_settings_get_default ();
453 cursor_blink_time = GetCaretBlinkTime ();
454 g_object_set (settings, "gtk-cursor-blink", cursor_blink_time > 0, NULL);
456 if (cursor_blink_time > 0)
458 g_object_set (settings, "gtk-cursor-blink-time",
459 2 * cursor_blink_time, NULL);
462 g_object_set (settings, "gtk-double-click-distance",
463 GetSystemMetrics (SM_CXDOUBLECLK), NULL);
464 g_object_set (settings, "gtk-double-click-time", GetDoubleClickTime (),
466 g_object_set (settings, "gtk-dnd-drag-threshold",
467 GetSystemMetrics (SM_CXDRAG), NULL);
469 setup_menu_settings (settings);
472 http://library.gnome.org/devel/gtk/stable/GtkSettings.html
473 http://msdn.microsoft.com/library/default.asp?url=/library/en-us/sysinfo/base/systemparametersinfo.asp
474 http://msdn.microsoft.com/library/default.asp?url=/library/en-us/sysinfo/base/getsystemmetrics.asp */
478 setup_system_font (GtkStyle *style)
480 char buf[256], *font; /* It's okay, lfFaceName is smaller than 32
483 if ((font = sys_font_to_pango_font (XP_THEME_CLASS_TEXT,
484 XP_THEME_FONT_MESSAGE,
485 buf, sizeof (buf))) != NULL)
487 if (style->font_desc)
489 pango_font_description_free (style->font_desc);
492 style->font_desc = pango_font_description_from_string (font);
497 sys_color_to_gtk_color (XpThemeClass klazz, int id, GdkColor * pcolor)
501 if (!xp_theme_get_system_color (klazz, id, &color))
502 color = GetSysColor (id);
504 pcolor->pixel = color;
505 pcolor->red = (GetRValue (color) << 8) | GetRValue (color);
506 pcolor->green = (GetGValue (color) << 8) | GetGValue (color);
507 pcolor->blue = (GetBValue (color) << 8) | GetBValue (color);
511 get_system_metric (XpThemeClass klazz, int id)
515 if (!xp_theme_get_system_metric (klazz, id, &rval))
516 rval = GetSystemMetrics (id);
522 setup_msw_rc_style (void)
524 char buf[1024], font_buf[256], *font_ptr;
525 char menu_bar_prelight_str[128];
528 GdkColor menu_text_color;
529 GdkColor tooltip_back;
530 GdkColor tooltip_fore;
533 GdkColor progress_back;
535 GdkColor fg_prelight;
536 GdkColor bg_prelight;
537 GdkColor base_prelight;
538 GdkColor text_prelight;
541 sys_color_to_gtk_color (get_windows_version () >= VISTA_VERSION ? XP_THEME_CLASS_MENU : XP_THEME_CLASS_TEXT,
542 get_windows_version () >= VISTA_VERSION ? COLOR_MENUTEXT : COLOR_HIGHLIGHTTEXT,
544 sys_color_to_gtk_color (XP_THEME_CLASS_TEXT, COLOR_HIGHLIGHT, &bg_prelight);
545 sys_color_to_gtk_color (XP_THEME_CLASS_TEXT, COLOR_HIGHLIGHT,
547 sys_color_to_gtk_color (XP_THEME_CLASS_TEXT, COLOR_HIGHLIGHTTEXT,
550 sys_color_to_gtk_color (XP_THEME_CLASS_MENU, COLOR_MENUTEXT,
552 sys_color_to_gtk_color (XP_THEME_CLASS_MENU, COLOR_MENU, &menu_color);
555 sys_color_to_gtk_color (XP_THEME_CLASS_TOOLTIP, COLOR_INFOTEXT,
557 sys_color_to_gtk_color (XP_THEME_CLASS_TOOLTIP, COLOR_INFOBK,
560 /* text on push buttons. TODO: button shadows, backgrounds, and
562 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNTEXT, &btn_fore);
563 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNFACE, &btn_face);
565 /* progress bar background color */
566 sys_color_to_gtk_color (XP_THEME_CLASS_PROGRESS, COLOR_HIGHLIGHT,
569 /* Enable coloring for menus. */
571 sys_font_to_pango_font (XP_THEME_CLASS_MENU, XP_THEME_FONT_MENU,
572 font_buf, sizeof (font_buf));
573 g_snprintf (buf, sizeof (buf),
574 "style \"msw-menu\" = \"msw-default\"\n" "{\n"
575 "GtkMenuItem::toggle-spacing = 8\n"
576 "fg[PRELIGHT] = { %d, %d, %d }\n"
577 "bg[PRELIGHT] = { %d, %d, %d }\n"
578 "text[PRELIGHT] = { %d, %d, %d }\n"
579 "base[PRELIGHT] = { %d, %d, %d }\n"
580 "fg[NORMAL] = { %d, %d, %d }\n"
581 "bg[NORMAL] = { %d, %d, %d }\n" "%s = \"%s\"\n"
582 "}widget_class \"*MenuItem*\" style \"msw-menu\"\n"
583 "widget_class \"*GtkMenu\" style \"msw-menu\"\n"
584 "widget_class \"*GtkMenuShell*\" style \"msw-menu\"\n",
585 fg_prelight.red, fg_prelight.green, fg_prelight.blue,
586 bg_prelight.red, bg_prelight.green, bg_prelight.blue,
587 text_prelight.red, text_prelight.green, text_prelight.blue,
588 base_prelight.red, base_prelight.green, base_prelight.blue,
589 menu_text_color.red, menu_text_color.green,
590 menu_text_color.blue, menu_color.red, menu_color.green,
591 menu_color.blue, (font_ptr ? "font_name" : "#"),
592 (font_ptr ? font_ptr : " font name should go here"));
593 gtk_rc_parse_string (buf);
595 if (xp_theme_is_active ())
597 *menu_bar_prelight_str = '\0';
601 g_snprintf (menu_bar_prelight_str, sizeof (menu_bar_prelight_str),
602 "fg[PRELIGHT] = { %d, %d, %d }\n",
603 menu_text_color.red, menu_text_color.green,
604 menu_text_color.blue);
607 /* Enable coloring for menu bars. */
608 g_snprintf (buf, sizeof (buf),
609 "style \"msw-menu-bar\" = \"msw-menu\"\n"
611 "bg[NORMAL] = { %d, %d, %d }\n"
612 "%s" "GtkMenuBar::shadow-type = %d\n"
614 FIXME: This should be enabled once gtk+ support
615 GtkMenuBar::prelight-item style property.
617 /* "GtkMenuBar::prelight-item = 1\n" */
618 "}widget_class \"*MenuBar*\" style \"msw-menu-bar\"\n",
619 btn_face.red, btn_face.green, btn_face.blue,
620 menu_bar_prelight_str, xp_theme_is_active ()? 0 : 2);
621 gtk_rc_parse_string (buf);
623 g_snprintf (buf, sizeof (buf),
624 "style \"msw-toolbar\" = \"msw-default\"\n"
626 "GtkHandleBox::shadow-type = %s\n"
627 "GtkToolbar::shadow-type = %s\n"
628 "}widget_class \"*HandleBox*\" style \"msw-toolbar\"\n",
629 "etched-in", "etched-in");
630 gtk_rc_parse_string (buf);
632 /* enable tooltip fonts */
633 font_ptr = sys_font_to_pango_font (XP_THEME_CLASS_STATUS, XP_THEME_FONT_STATUS,
634 font_buf, sizeof (font_buf));
635 g_snprintf (buf, sizeof (buf),
636 "style \"msw-tooltips-caption\" = \"msw-default\"\n"
637 "{fg[NORMAL] = { %d, %d, %d }\n" "%s = \"%s\"\n"
638 "}widget \"gtk-tooltips.GtkLabel\" style \"msw-tooltips-caption\"\n"
639 "widget \"gtk-tooltip.GtkLabel\" style \"msw-tooltips-caption\"\n",
640 tooltip_fore.red, tooltip_fore.green, tooltip_fore.blue,
641 (font_ptr ? "font_name" : "#"),
642 (font_ptr ? font_ptr : " font name should go here"));
643 gtk_rc_parse_string (buf);
645 g_snprintf (buf, sizeof (buf),
646 "style \"msw-tooltips\" = \"msw-default\"\n"
647 "{bg[NORMAL] = { %d, %d, %d }\n"
648 "}widget \"gtk-tooltips*\" style \"msw-tooltips\"\n"
649 "widget \"gtk-tooltip*\" style \"msw-tooltips\"\n",
650 tooltip_back.red, tooltip_back.green, tooltip_back.blue);
651 gtk_rc_parse_string (buf);
653 /* enable font theming for status bars */
654 font_ptr = sys_font_to_pango_font (XP_THEME_CLASS_STATUS, XP_THEME_FONT_STATUS,
655 font_buf, sizeof (font_buf));
656 g_snprintf (buf, sizeof (buf),
657 "style \"msw-status\" = \"msw-default\"\n" "{%s = \"%s\"\n"
658 "bg[NORMAL] = { %d, %d, %d }\n"
659 "}widget_class \"*Status*\" style \"msw-status\"\n",
660 (font_ptr ? "font_name" : "#"),
661 (font_ptr ? font_ptr : " font name should go here"),
662 btn_face.red, btn_face.green, btn_face.blue);
663 gtk_rc_parse_string (buf);
665 /* enable coloring for text on buttons
666 * TODO: use GetThemeMetric for the border and outside border
667 * TODO: child-displacement-x & y should be 0 when XP theme is active */
668 g_snprintf (buf, sizeof (buf),
669 "style \"msw-button\" = \"msw-default\"\n"
671 "bg[NORMAL] = { %d, %d, %d }\n"
672 "bg[PRELIGHT] = { %d, %d, %d }\n"
673 "bg[INSENSITIVE] = { %d, %d, %d }\n"
674 "fg[PRELIGHT] = { %d, %d, %d }\n"
675 "GtkButton::default-border = { 0, 0, 0, 0 }\n"
676 "GtkButton::default-outside-border = { 0, 0, 0, 0 }\n"
677 "GtkButton::child-displacement-x = 1\n"
678 "GtkButton::child-displacement-y = 1\n"
679 "GtkButton::focus-padding = %d\n"
680 "}widget_class \"*Button*\" style \"msw-button\"\n",
681 btn_face.red, btn_face.green, btn_face.blue,
682 btn_face.red, btn_face.green, btn_face.blue,
683 btn_face.red, btn_face.green, btn_face.blue,
684 btn_fore.red, btn_fore.green, btn_fore.blue,
685 xp_theme_is_active ()? 1 : 2);
686 gtk_rc_parse_string (buf);
688 /* enable coloring for progress bars */
689 g_snprintf (buf, sizeof (buf),
690 "style \"msw-progress\" = \"msw-default\"\n"
691 "{bg[PRELIGHT] = { %d, %d, %d }\n"
692 "bg[NORMAL] = { %d, %d, %d }\n"
693 "}widget_class \"*Progress*\" style \"msw-progress\"\n",
697 btn_face.red, btn_face.green, btn_face.blue);
698 gtk_rc_parse_string (buf);
700 /* scrollbar thumb width and height */
701 g_snprintf (buf, sizeof (buf),
702 "style \"msw-vscrollbar\" = \"msw-default\"\n"
703 "{GtkRange::slider-width = %d\n"
704 "GtkRange::stepper-size = %d\n"
705 "GtkRange::stepper-spacing = 0\n"
706 "GtkRange::trough_border = 0\n"
707 "GtkScale::slider-length = %d\n"
708 "GtkScrollbar::min-slider-length = 8\n"
709 "}widget_class \"*VScrollbar*\" style \"msw-vscrollbar\"\n"
710 "widget_class \"*VScale*\" style \"msw-vscrollbar\"\n",
711 GetSystemMetrics (SM_CYVTHUMB),
712 get_system_metric (XP_THEME_CLASS_SCROLLBAR, SM_CXVSCROLL), 11);
713 gtk_rc_parse_string (buf);
715 g_snprintf (buf, sizeof (buf),
716 "style \"msw-hscrollbar\" = \"msw-default\"\n"
717 "{GtkRange::slider-width = %d\n"
718 "GtkRange::stepper-size = %d\n"
719 "GtkRange::stepper-spacing = 0\n"
720 "GtkRange::trough_border = 0\n"
721 "GtkScale::slider-length = %d\n"
722 "GtkScrollbar::min-slider-length = 8\n"
723 "}widget_class \"*HScrollbar*\" style \"msw-hscrollbar\"\n"
724 "widget_class \"*HScale*\" style \"msw-hscrollbar\"\n",
725 GetSystemMetrics (SM_CXHTHUMB),
726 get_system_metric (XP_THEME_CLASS_SCROLLBAR, SM_CYHSCROLL), 11);
727 gtk_rc_parse_string (buf);
729 gtk_rc_parse_string ("style \"msw-scrolled-window\" = \"msw-default\"\n"
730 "{GtkScrolledWindow::scrollbars-within-bevel = 1}\n"
731 "class \"GtkScrolledWindow\" style \"msw-scrolled-window\"\n");
733 /* radio/check button sizes */
734 g_snprintf (buf, sizeof (buf),
735 "style \"msw-checkbutton\" = \"msw-button\"\n"
736 "{GtkCheckButton::indicator-size = 13\n"
737 "}widget_class \"*CheckButton*\" style \"msw-checkbutton\"\n"
738 "widget_class \"*RadioButton*\" style \"msw-checkbutton\"\n");
739 gtk_rc_parse_string (buf);
741 /* size of combo box toggle button */
742 g_snprintf (buf, sizeof (buf),
743 "style \"msw-combobox-button\" = \"msw-default\"\n"
747 "GtkButton::default-border = { 0, 0, 0, 0 }\n"
748 "GtkButton::default-outside-border = { 0, 0, 0, 0 }\n"
749 "GtkButton::child-displacement-x = 0\n"
750 "GtkButton::child-displacement-y = 0\n"
751 "GtkWidget::focus-padding = 0\n"
752 "GtkWidget::focus-line-width = 0\n"
754 "widget_class \"*ComboBox*ToggleButton*\" style \"msw-combobox-button\"\n");
755 gtk_rc_parse_string (buf);
757 g_snprintf (buf, sizeof (buf),
758 "style \"msw-combobox\" = \"msw-default\"\n"
760 "GtkComboBox::shadow-type = in\n"
764 "class \"GtkComboBox\" style \"msw-combobox\"\n",
765 xp_theme_is_active()? 1 : GetSystemMetrics (SM_CXEDGE),
766 xp_theme_is_active()? 1 : GetSystemMetrics (SM_CYEDGE));
767 gtk_rc_parse_string (buf);
769 /* size of tree view header */
770 g_snprintf (buf, sizeof (buf),
771 "style \"msw-header-button\" = \"msw-default\"\n"
775 "GtkWidget::draw-border = {0, 0, 0, 0}\n"
776 "GtkButton::default-border = { 0, 0, 0, 0 }\n"
777 "GtkButton::default-outside-border = { 0, 0, 0, 0 }\n"
778 "GtkButton::child-displacement-x = 0\n"
779 "GtkButton::child-displacement-y = 0\n"
780 "GtkWidget::focus-padding = 0\n"
781 "GtkWidget::focus-line-width = 0\n"
783 "widget_class \"*TreeView*Button*\" style \"msw-header-button\"\n");
784 gtk_rc_parse_string (buf);
786 /* FIXME: This should be enabled once gtk+ support GtkNotebok::prelight-tab */
787 /* enable prelight tab of GtkNotebook */
789 g_snprintf (buf, sizeof (buf),
790 "style \"msw-notebook\" = \"msw-default\"\n"
791 "{GtkNotebook::prelight-tab=1\n"
792 "}widget_class \"*Notebook*\" style \"msw-notebook\"\n");
793 gtk_rc_parse_string (buf);
796 /* FIXME: This should be enabled once gtk+ support GtkTreeView::full-row-focus */
798 g_snprintf (buf, sizeof (buf),
799 "style \"msw-treeview\" = \"msw-default\"\n"
800 "{GtkTreeView::full-row-focus=0\n"
801 "}widget_class \"*TreeView*\" style \"msw-treeview\"\n");
802 gtk_rc_parse_string (buf);
807 setup_system_styles (GtkStyle *style)
811 /* Default background */
812 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNFACE,
813 &style->bg[GTK_STATE_NORMAL]);
814 sys_color_to_gtk_color (XP_THEME_CLASS_TEXT, COLOR_HIGHLIGHT,
815 &style->bg[GTK_STATE_SELECTED]);
816 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNFACE,
817 &style->bg[GTK_STATE_INSENSITIVE]);
818 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNFACE,
819 &style->bg[GTK_STATE_ACTIVE]);
820 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNFACE,
821 &style->bg[GTK_STATE_PRELIGHT]);
824 sys_color_to_gtk_color (XP_THEME_CLASS_WINDOW, COLOR_WINDOW,
825 &style->base[GTK_STATE_NORMAL]);
826 sys_color_to_gtk_color (XP_THEME_CLASS_TEXT, COLOR_HIGHLIGHT,
827 &style->base[GTK_STATE_SELECTED]);
828 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNFACE,
829 &style->base[GTK_STATE_INSENSITIVE]);
830 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNFACE,
831 &style->base[GTK_STATE_ACTIVE]);
832 sys_color_to_gtk_color (XP_THEME_CLASS_WINDOW, COLOR_WINDOW,
833 &style->base[GTK_STATE_PRELIGHT]);
836 sys_color_to_gtk_color (XP_THEME_CLASS_WINDOW, COLOR_WINDOWTEXT,
837 &style->text[GTK_STATE_NORMAL]);
838 sys_color_to_gtk_color (XP_THEME_CLASS_TEXT, COLOR_HIGHLIGHTTEXT,
839 &style->text[GTK_STATE_SELECTED]);
840 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_GRAYTEXT,
841 &style->text[GTK_STATE_INSENSITIVE]);
842 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNTEXT,
843 &style->text[GTK_STATE_ACTIVE]);
844 sys_color_to_gtk_color (XP_THEME_CLASS_WINDOW, COLOR_WINDOWTEXT,
845 &style->text[GTK_STATE_PRELIGHT]);
847 /* Default foreground */
848 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNTEXT,
849 &style->fg[GTK_STATE_NORMAL]);
850 sys_color_to_gtk_color (XP_THEME_CLASS_TEXT, COLOR_HIGHLIGHTTEXT,
851 &style->fg[GTK_STATE_SELECTED]);
852 sys_color_to_gtk_color (XP_THEME_CLASS_TEXT, COLOR_GRAYTEXT,
853 &style->fg[GTK_STATE_INSENSITIVE]);
854 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_BTNTEXT,
855 &style->fg[GTK_STATE_ACTIVE]);
856 sys_color_to_gtk_color (XP_THEME_CLASS_WINDOW, COLOR_WINDOWTEXT,
857 &style->fg[GTK_STATE_PRELIGHT]);
859 for (i = 0; i < 5; i++)
861 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_3DSHADOW,
863 sys_color_to_gtk_color (XP_THEME_CLASS_BUTTON, COLOR_3DHILIGHT,
866 style->mid[i].red = (style->light[i].red + style->dark[i].red) / 2;
867 style->mid[i].green =
868 (style->light[i].green + style->dark[i].green) / 2;
869 style->mid[i].blue = (style->light[i].blue + style->dark[i].blue) / 2;
871 style->text_aa[i].red = (style->text[i].red + style->base[i].red) / 2;
872 style->text_aa[i].green =
873 (style->text[i].green + style->base[i].green) / 2;
874 style->text_aa[i].blue =
875 (style->text[i].blue + style->base[i].blue) / 2;
879 static XpThemeElement
880 map_gtk_progress_bar_to_xp (GtkProgressBar *progress_bar, gboolean trough)
884 switch (gtk_orientable_get_orientation (GTK_ORIENTABLE (progress_bar)))
886 case GTK_ORIENTATION_HORIZONTAL:
888 ? XP_THEME_ELEMENT_PROGRESS_TROUGH_H
889 : XP_THEME_ELEMENT_PROGRESS_BAR_H;
894 ? XP_THEME_ELEMENT_PROGRESS_TROUGH_V
895 : XP_THEME_ELEMENT_PROGRESS_BAR_V;
903 is_combo_box_child (GtkWidget *w)
910 for (tmp = gtk_widget_get_parent (w); tmp; tmp = gtk_widget_get_parent (tmp))
912 if (GTK_IS_COMBO_BOX (tmp))
919 /* This function is not needed anymore */
921 combo_box_draw_arrow (GtkStyle *style,
926 if (xp_theme_is_active ())
929 if (widget && GTK_IS_TOGGLE_BUTTON (widget->parent))
936 dc = get_window_dc (style, cr, state, &dc_info, area->x, area->y, area->width,
937 area->height, &rect);
938 border = (GTK_TOGGLE_BUTTON (gtk_widget_get_parent (widget))->
939 active ? DFCS_PUSHED | DFCS_FLAT : 0);
941 InflateRect (&rect, 1, 1);
942 DrawFrameControl (dc, &rect, DFC_SCROLL, DFCS_SCROLLDOWN | border);
944 release_window_dc (&dc_info);
953 draw_part (cairo_t *cr,
954 GdkColor *gc, gint x, gint y, Part part)
956 if (!parts[part].bmap)
958 parts[part].bmap = cairo_image_surface_create_for_data ((unsigned char *)parts[part].bits,
960 PART_SIZE, PART_SIZE, 4);
963 gdk_cairo_set_source_color (cr, gc);
964 cairo_mask_surface (cr, parts[part].bmap, x, y);
968 draw_check (GtkStyle *style,
971 GtkShadowType shadow,
973 const gchar *detail, gint x, gint y, gint width, gint height)
975 x -= (1 + PART_SIZE - width) / 2;
976 y -= (1 + PART_SIZE - height) / 2;
978 if (detail && strcmp (detail, "check") == 0) /* Menu item */
980 if (shadow == GTK_SHADOW_IN)
982 draw_part (cr, &style->black, x, y, CHECK_TEXT);
983 draw_part (cr, &style->dark[state], x, y, CHECK_AA);
988 XpThemeElement theme_elt = XP_THEME_ELEMENT_CHECKBOX;
991 case GTK_SHADOW_ETCHED_IN:
992 theme_elt = XP_THEME_ELEMENT_INCONSISTENT_CHECKBOX;
996 theme_elt = XP_THEME_ELEMENT_PRESSED_CHECKBOX;
1003 if (!xp_theme_draw (cr, theme_elt,
1004 style, x, y, width, height, state))
1006 if (detail && !strcmp (detail, "cellcheck"))
1007 state = GTK_STATE_NORMAL;
1009 draw_part (cr, &style->black, x, y, CHECK_BLACK);
1010 draw_part (cr, &style->dark[state], x, y, CHECK_DARK);
1011 draw_part (cr, &style->mid[state], x, y, CHECK_MID);
1012 draw_part (cr, &style->light[state], x, y, CHECK_LIGHT);
1013 draw_part (cr, &style->base[state], x, y, CHECK_BASE);
1015 if (shadow == GTK_SHADOW_IN)
1017 draw_part (cr, &style->text[state], x, y, CHECK_TEXT);
1018 draw_part (cr, &style->text_aa[state], x, y, CHECK_AA);
1020 else if (shadow == GTK_SHADOW_ETCHED_IN)
1022 draw_part (cr, &style->text[state], x, y, CHECK_INCONSISTENT);
1023 draw_part (cr, &style->text_aa[state], x, y, CHECK_AA);
1030 draw_expander (GtkStyle *style,
1034 const gchar *detail,
1035 gint x, gint y, GtkExpanderStyle expander_style)
1038 gint expander_semi_size;
1039 XpThemeElement xp_expander;
1041 gtk_widget_style_get (widget, "expander_size", &expander_size, NULL);
1043 switch (expander_style)
1045 case GTK_EXPANDER_COLLAPSED:
1046 case GTK_EXPANDER_SEMI_COLLAPSED:
1047 xp_expander = XP_THEME_ELEMENT_TREEVIEW_EXPANDER_CLOSED;
1051 xp_expander = XP_THEME_ELEMENT_TREEVIEW_EXPANDER_OPENED;
1055 if ((expander_size % 2) == 0)
1058 if (expander_size > 2)
1062 gdk_cairo_set_source_color (cr, &style->fg[state]);
1065 expander_semi_size = expander_size / 2;
1066 x -= expander_semi_size;
1067 y -= expander_semi_size;
1069 if (!xp_theme_draw (cr, xp_expander, style,
1070 x, y, expander_size, expander_size, state))
1078 dc = get_window_dc (style, cr, state, &dc_info, x, y, expander_size,
1079 expander_size, &rect);
1080 FrameRect (dc, &rect, GetSysColorBrush (COLOR_GRAYTEXT));
1081 InflateRect (&rect, -1, -1);
1082 FillRect (dc, &rect,
1083 GetSysColorBrush (state ==
1084 GTK_STATE_INSENSITIVE ? COLOR_BTNFACE :
1087 InflateRect (&rect, -1, -1);
1089 pen = CreatePen (PS_SOLID, 1, GetSysColor (COLOR_WINDOWTEXT));
1090 old_pen = SelectObject (dc, pen);
1092 MoveToEx (dc, rect.left, rect.top - 2 + expander_semi_size, NULL);
1093 LineTo (dc, rect.right, rect.top - 2 + expander_semi_size);
1095 if (expander_style == GTK_EXPANDER_COLLAPSED ||
1096 expander_style == GTK_EXPANDER_SEMI_COLLAPSED)
1098 MoveToEx (dc, rect.left - 2 + expander_semi_size, rect.top, NULL);
1099 LineTo (dc, rect.left - 2 + expander_semi_size, rect.bottom);
1102 SelectObject (dc, old_pen);
1104 release_window_dc (&dc_info);
1109 draw_option (GtkStyle *style,
1112 GtkShadowType shadow,
1114 const gchar *detail, gint x, gint y, gint width, gint height)
1116 x -= (1 + PART_SIZE - width) / 2;
1117 y -= (1 + PART_SIZE - height) / 2;
1119 if (detail && strcmp (detail, "option") == 0) /* Menu item */
1121 if (shadow == GTK_SHADOW_IN)
1123 draw_part (cr, &style->fg[state], x, y, RADIO_TEXT);
1128 if (xp_theme_draw (cr, shadow == GTK_SHADOW_IN
1129 ? XP_THEME_ELEMENT_PRESSED_RADIO_BUTTON
1130 : XP_THEME_ELEMENT_RADIO_BUTTON,
1131 style, x, y, width, height, state))
1136 if (detail && !strcmp (detail, "cellradio"))
1137 state = GTK_STATE_NORMAL;
1139 draw_part (cr, &style->black, x, y, RADIO_BLACK);
1140 draw_part (cr, &style->dark[state], x, y, RADIO_DARK);
1141 draw_part (cr, &style->mid[state], x, y, RADIO_MID);
1142 draw_part (cr, &style->light[state], x, y, RADIO_LIGHT);
1143 draw_part (cr, &style->base[state], x, y, RADIO_BASE);
1145 if (shadow == GTK_SHADOW_IN)
1146 draw_part (cr, &style->text[state], x, y, RADIO_TEXT);
1152 draw_varrow (cairo_t *cr,
1154 GtkShadowType shadow_type,
1155 GtkArrowType arrow_type, gint x, gint y, gint width, gint height)
1158 gint y_start, y_increment;
1161 width = width + width % 2 - 1; /* Force odd */
1162 steps = 1 + width / 2;
1163 extra = height - steps;
1165 if (arrow_type == GTK_ARROW_DOWN)
1172 y_start = y + height - 1;
1176 for (i = extra; i < height; i++)
1178 _cairo_draw_line (cr, gc,
1179 x + (i - extra), y_start + i * y_increment,
1180 x + width - (i - extra) - 1, y_start + i * y_increment);
1185 draw_harrow (cairo_t *cr,
1187 GtkShadowType shadow_type,
1188 GtkArrowType arrow_type, gint x, gint y, gint width, gint height)
1191 gint x_start, x_increment;
1194 height = height + height % 2 - 1; /* Force odd */
1195 steps = 1 + height / 2;
1196 extra = width - steps;
1198 if (arrow_type == GTK_ARROW_RIGHT)
1205 x_start = x + width - 1;
1209 for (i = extra; i < width; i++)
1211 _cairo_draw_line (cr, gc,
1212 x_start + i * x_increment, y + (i - extra),
1213 x_start + i * x_increment, y + height - (i - extra) - 1);
1217 /* This function makes up for some brokeness in gtkrange.c
1218 * where we never get the full arrow of the stepper button
1219 * and the type of button in a single drawing function.
1221 * It doesn't work correctly when the scrollbar is squished
1222 * to the point we don't have room for full-sized steppers.
1225 reverse_engineer_stepper_box (GtkWidget *range,
1226 GtkArrowType arrow_type,
1227 gint *x, gint *y, gint *width, gint *height)
1229 gint slider_width = 14, stepper_size = 14;
1235 gtk_widget_style_get (range,
1236 "slider_width", &slider_width,
1237 "stepper_size", &stepper_size, NULL);
1240 if (arrow_type == GTK_ARROW_UP || arrow_type == GTK_ARROW_DOWN)
1242 box_width = slider_width;
1243 box_height = stepper_size;
1247 box_width = stepper_size;
1248 box_height = slider_width;
1251 *x = *x - (box_width - *width) / 2;
1252 *y = *y - (box_height - *height) / 2;
1254 *height = box_height;
1257 static XpThemeElement
1258 to_xp_arrow (GtkArrowType arrow_type)
1260 XpThemeElement xp_arrow;
1265 xp_arrow = XP_THEME_ELEMENT_ARROW_UP;
1268 case GTK_ARROW_DOWN:
1269 xp_arrow = XP_THEME_ELEMENT_ARROW_DOWN;
1272 case GTK_ARROW_LEFT:
1273 xp_arrow = XP_THEME_ELEMENT_ARROW_LEFT;
1277 xp_arrow = XP_THEME_ELEMENT_ARROW_RIGHT;
1285 draw_arrow (GtkStyle *style,
1288 GtkShadowType shadow,
1290 const gchar *detail,
1291 GtkArrowType arrow_type,
1292 gboolean fill, gint x, gint y, gint width, gint height)
1299 name = gtk_widget_get_name (widget);
1301 if (GTK_IS_ARROW (widget) && is_combo_box_child (widget) && xp_theme_is_active ())
1304 if (detail && strcmp (detail, "spinbutton") == 0)
1306 if (xp_theme_is_drawable (XP_THEME_ELEMENT_SPIN_BUTTON_UP))
1313 if (arrow_type == GTK_ARROW_DOWN)
1317 if (state == GTK_STATE_ACTIVE)
1323 draw_varrow (cr, &style->fg[state], shadow,
1324 arrow_type, x, y, width, height);
1328 else if (detail && (!strcmp (detail, "vscrollbar")
1329 || !strcmp (detail, "hscrollbar")))
1331 gboolean is_disabled = FALSE;
1333 GtkScrollbar *scrollbar = GTK_SCROLLBAR (widget);
1337 gint box_width = width;
1338 gint box_height = height;
1340 reverse_engineer_stepper_box (widget, arrow_type,
1341 &box_x, &box_y, &box_width, &box_height);
1343 if (gtk_adjustment_get_page_size(gtk_range_get_adjustment(&scrollbar->range)) >=
1344 (gtk_adjustment_get_upper(gtk_range_get_adjustment(&scrollbar->range)) -
1345 gtk_adjustment_get_lower(gtk_range_get_adjustment(&scrollbar->range))))
1350 if (xp_theme_draw (cr, to_xp_arrow (arrow_type), style, box_x, box_y,
1351 box_width, box_height, state))
1359 btn_type = DFCS_SCROLLUP;
1362 case GTK_ARROW_DOWN:
1363 btn_type = DFCS_SCROLLDOWN;
1366 case GTK_ARROW_LEFT:
1367 btn_type = DFCS_SCROLLLEFT;
1370 case GTK_ARROW_RIGHT:
1371 btn_type = DFCS_SCROLLRIGHT;
1374 case GTK_ARROW_NONE:
1378 if (state == GTK_STATE_INSENSITIVE)
1380 btn_type |= DFCS_INACTIVE;
1385 dc = get_window_dc (style, cr, state, &dc_info,
1386 box_x, box_y, box_width, box_height, &rect);
1387 DrawFrameControl (dc, &rect, DFC_SCROLL,
1388 btn_type | (shadow ==
1389 GTK_SHADOW_IN ? (DFCS_PUSHED |
1391 release_window_dc (&dc_info);
1397 /* draw the toolbar chevrons - waiting for GTK 2.4 */
1398 if (name && !strcmp (name, "gtk-toolbar-arrow"))
1401 (cr, XP_THEME_ELEMENT_REBAR_CHEVRON, style, x, y,
1402 width, height, state))
1407 /* probably a gtk combo box on a toolbar */
1408 else if (0 /* gtk_widget_get_parent (widget) && GTK_IS_BUTTON
1409 (gtk_widget_get_parent (widget)) */ )
1411 GtkAllocation allocation;
1413 gtk_widget_get_allocation (widget, &allocation);
1415 (cr, XP_THEME_ELEMENT_COMBOBUTTON, style, x - 3,
1416 allocation.y + 1, width + 5,
1417 allocation.height - 4, state))
1423 if (arrow_type == GTK_ARROW_UP || arrow_type == GTK_ARROW_DOWN)
1425 x += (width - 7) / 2;
1426 y += (height - 5) / 2;
1428 draw_varrow (cr, &style->fg[state], shadow,
1429 arrow_type, x, y, 7, 5);
1433 x += (width - 5) / 2;
1434 y += (height - 7) / 2;
1436 draw_harrow (cr, &style->fg[state], shadow,
1437 arrow_type, x, y, 5, 7);
1443 option_menu_get_props (GtkWidget *widget,
1444 GtkRequisition *indicator_size,
1445 GtkBorder *indicator_spacing)
1447 GtkRequisition *tmp_size = NULL;
1448 GtkBorder *tmp_spacing = NULL;
1451 gtk_widget_style_get (widget,
1452 "indicator_size", &tmp_size,
1453 "indicator_spacing", &tmp_spacing, NULL);
1457 *indicator_size = *tmp_size;
1458 gtk_requisition_free (tmp_size);
1462 *indicator_size = default_option_indicator_size;
1467 *indicator_spacing = *tmp_spacing;
1468 gtk_border_free (tmp_spacing);
1472 *indicator_spacing = default_option_indicator_spacing;
1477 is_toolbar_child (GtkWidget *wid)
1481 if (GTK_IS_TOOLBAR (wid) || GTK_IS_HANDLE_BOX (wid))
1484 wid = gtk_widget_get_parent (wid);
1491 is_menu_tool_button_child (GtkWidget *wid)
1495 if (GTK_IS_MENU_TOOL_BUTTON (wid))
1498 wid = gtk_widget_get_parent (wid);
1508 g_light_pen = CreatePen (PS_SOLID | PS_INSIDEFRAME, 1,
1509 GetSysColor (COLOR_BTNHIGHLIGHT));
1520 g_dark_pen = CreatePen (PS_SOLID | PS_INSIDEFRAME, 1,
1521 GetSysColor (COLOR_BTNSHADOW));
1528 draw_3d_border (HDC hdc, RECT *rc, gboolean sunken)
1535 pen1 = get_dark_pen ();
1536 pen2 = get_light_pen ();
1540 pen1 = get_light_pen ();
1541 pen2 = get_dark_pen ();
1544 MoveToEx (hdc, rc->left, rc->bottom - 1, NULL);
1546 old_pen = SelectObject (hdc, pen1);
1547 LineTo (hdc, rc->left, rc->top);
1548 LineTo (hdc, rc->right - 1, rc->top);
1549 SelectObject (hdc, old_pen);
1551 old_pen = SelectObject (hdc, pen2);
1552 LineTo (hdc, rc->right - 1, rc->bottom - 1);
1553 LineTo (hdc, rc->left, rc->bottom - 1);
1554 SelectObject (hdc, old_pen);
1558 draw_menu_item (cairo_t *cr, GtkWidget *widget, GtkStyle *style,
1559 gint x, gint y, gint width, gint height,
1560 GtkStateType state_type)
1568 if (xp_theme_is_active ())
1570 return (xp_theme_draw (cr, XP_THEME_ELEMENT_MENU_ITEM, style,
1571 x, y, width, height, state_type));
1574 if ((parent = gtk_widget_get_parent (widget))
1575 && GTK_IS_MENU_BAR (parent) && !xp_theme_is_active ())
1577 bar = GTK_MENU_SHELL (parent);
1579 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
1581 if (state_type == GTK_STATE_PRELIGHT)
1583 draw_3d_border (dc, &rect, bar->priv->active);
1586 release_window_dc (&dc_info);
1595 get_dither_brush (void)
1598 HBITMAP pattern_bmp;
1602 return g_dither_brush;
1604 for (i = 0; i < 8; i++)
1606 pattern[i] = (WORD) (0x5555 << (i & 1));
1609 pattern_bmp = CreateBitmap (8, 8, 1, 1, &pattern);
1613 g_dither_brush = CreatePatternBrush (pattern_bmp);
1614 DeleteObject (pattern_bmp);
1617 return g_dither_brush;
1621 draw_tool_button (cairo_t *cr, GtkWidget *widget, GtkStyle *style,
1622 gint x, gint y, gint width, gint height,
1623 GtkStateType state_type)
1628 gboolean is_toggled = FALSE;
1630 if (xp_theme_is_active ())
1632 return (xp_theme_draw (cr, XP_THEME_ELEMENT_TOOLBAR_BUTTON, style,
1633 x, y, width, height, state_type));
1636 if (GTK_IS_TOGGLE_BUTTON (widget))
1638 if (gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (widget)))
1644 if (state_type != GTK_STATE_PRELIGHT
1645 && state_type != GTK_STATE_ACTIVE && !is_toggled)
1650 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
1651 if (state_type == GTK_STATE_PRELIGHT)
1655 FillRect (dc, &rect, GetSysColorBrush (COLOR_BTNFACE));
1658 draw_3d_border (dc, &rect, is_toggled);
1660 else if (state_type == GTK_STATE_ACTIVE)
1662 if (is_toggled && !is_menu_tool_button_child (gtk_widget_get_parent (widget)))
1664 SetTextColor (dc, GetSysColor (COLOR_3DHILIGHT));
1665 SetBkColor (dc, GetSysColor (COLOR_BTNFACE));
1666 FillRect (dc, &rect, get_dither_brush ());
1669 draw_3d_border (dc, &rect, TRUE);
1672 release_window_dc (&dc_info);
1678 draw_push_button (cairo_t *cr, GtkWidget *widget, GtkStyle *style,
1679 gint x, gint y, gint width, gint height,
1680 GtkStateType state_type, gboolean is_default)
1686 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
1688 if (GTK_IS_TOGGLE_BUTTON (widget))
1690 if (state_type == GTK_STATE_PRELIGHT &&
1691 gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (widget)))
1693 state_type = GTK_STATE_ACTIVE;
1697 if (state_type == GTK_STATE_ACTIVE)
1699 if (GTK_IS_TOGGLE_BUTTON (widget))
1701 DrawEdge (dc, &rect, EDGE_SUNKEN, BF_RECT | BF_ADJUST);
1702 SetTextColor (dc, GetSysColor (COLOR_3DHILIGHT));
1703 SetBkColor (dc, GetSysColor (COLOR_BTNFACE));
1704 FillRect (dc, &rect, get_dither_brush ());
1708 FrameRect (dc, &rect, GetSysColorBrush (COLOR_WINDOWFRAME));
1709 InflateRect (&rect, -1, -1);
1710 FrameRect (dc, &rect, GetSysColorBrush (COLOR_BTNSHADOW));
1711 InflateRect (&rect, -1, -1);
1712 FillRect (dc, &rect, GetSysColorBrush (COLOR_BTNFACE));
1717 if (is_default || gtk_widget_has_focus (widget))
1719 FrameRect (dc, &rect, GetSysColorBrush (COLOR_WINDOWFRAME));
1720 InflateRect (&rect, -1, -1);
1723 DrawFrameControl (dc, &rect, DFC_BUTTON, DFCS_BUTTONPUSH);
1726 release_window_dc (&dc_info);
1730 draw_box (GtkStyle *style,
1732 GtkStateType state_type,
1733 GtkShadowType shadow_type,
1735 const gchar *detail, gint x, gint y, gint width, gint height)
1737 if (is_combo_box_child (widget) && detail && !strcmp (detail, "button"))
1745 border = (gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (widget)) ? DFCS_PUSHED | DFCS_FLAT : 0);
1747 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
1748 DrawFrameControl (dc, &rect, DFC_SCROLL, DFCS_SCROLLDOWN | border);
1749 release_window_dc (&dc_info);
1751 if (xp_theme_is_active ()
1752 && xp_theme_draw (cr, XP_THEME_ELEMENT_COMBOBUTTON, style, x, y,
1753 width, height, state_type))
1755 cx = GetSystemMetrics(SM_CXVSCROLL);
1760 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width - cx, height, &rect);
1761 FillRect (dc, &rect, GetSysColorBrush (COLOR_WINDOW));
1762 release_window_dc (&dc_info);
1768 (!strcmp (detail, "button") || !strcmp (detail, "buttondefault")))
1770 if (GTK_IS_TREE_VIEW (gtk_widget_get_parent (widget)))
1773 (cr, XP_THEME_ELEMENT_LIST_HEADER, style, x, y,
1774 width, height, state_type))
1783 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
1785 DrawFrameControl (dc, &rect, DFC_BUTTON, DFCS_BUTTONPUSH |
1787 GTK_STATE_ACTIVE ? (DFCS_PUSHED | DFCS_FLAT)
1789 release_window_dc (&dc_info);
1792 else if (is_toolbar_child (gtk_widget_get_parent (widget))
1793 || (!GTK_IS_BUTTON (widget) ||
1794 (GTK_RELIEF_NONE == gtk_button_get_relief (GTK_BUTTON (widget)))))
1796 if (draw_tool_button (cr, widget, style, x, y,
1797 width, height, state_type))
1804 gboolean is_default = gtk_widget_has_default (widget);
1807 is_default ? XP_THEME_ELEMENT_DEFAULT_BUTTON :
1808 XP_THEME_ELEMENT_BUTTON, style, x, y, width, height,
1814 draw_push_button (cr, widget, style,
1815 x, y, width, height, state_type, is_default);
1822 else if (detail && !strcmp (detail, "spinbutton"))
1824 if (xp_theme_is_drawable (XP_THEME_ELEMENT_SPIN_BUTTON_UP))
1829 else if (detail && (!strcmp (detail, "spinbutton_up")
1830 || !strcmp (detail, "spinbutton_down")))
1832 if (!xp_theme_draw (cr,
1833 (!strcmp (detail, "spinbutton_up"))
1834 ? XP_THEME_ELEMENT_SPIN_BUTTON_UP
1835 : XP_THEME_ELEMENT_SPIN_BUTTON_DOWN,
1836 style, x, y, width, height, state_type))
1842 dc = get_window_dc (style, cr, state_type, &dc_info,
1843 x, y, width, height, &rect);
1844 DrawEdge (dc, &rect,
1846 GTK_STATE_ACTIVE ? EDGE_SUNKEN : EDGE_RAISED, BF_RECT);
1847 release_window_dc (&dc_info);
1851 else if (detail && !strcmp (detail, "slider"))
1853 if (GTK_IS_SCROLLBAR (widget))
1855 GtkScrollbar *scrollbar = GTK_SCROLLBAR (widget);
1856 gboolean is_v = GTK_IS_VSCROLLBAR (widget);
1858 if (xp_theme_draw (cr,
1860 ? XP_THEME_ELEMENT_SCROLLBAR_V
1861 : XP_THEME_ELEMENT_SCROLLBAR_H,
1862 style, x, y, width, height, state_type))
1864 XpThemeElement gripper =
1865 (is_v ? XP_THEME_ELEMENT_SCROLLBAR_GRIPPER_V :
1866 XP_THEME_ELEMENT_SCROLLBAR_GRIPPER_H);
1868 /* Do not display grippers on tiny scroll bars,
1869 the limit imposed is rather arbitrary, perhaps
1870 we can fetch the gripper geometry from
1871 somewhere and use that... */
1873 XP_THEME_ELEMENT_SCROLLBAR_GRIPPER_H
1876 XP_THEME_ELEMENT_SCROLLBAR_GRIPPER_V && height < 16))
1881 xp_theme_draw (cr, gripper, style, x, y,
1882 width, height, state_type);
1887 if (gtk_adjustment_get_page_size(gtk_range_get_adjustment(&scrollbar->range)) >=
1888 (gtk_adjustment_get_page_size(gtk_range_get_adjustment(&scrollbar->range)) -
1889 gtk_adjustment_get_page_size(gtk_range_get_adjustment(&scrollbar->range))))
1896 else if (detail && !strcmp (detail, "bar"))
1898 if (widget && GTK_IS_PROGRESS_BAR (widget))
1900 GtkProgressBar *progress_bar = GTK_PROGRESS_BAR (widget);
1901 XpThemeElement xp_progress_bar =
1902 map_gtk_progress_bar_to_xp (progress_bar, FALSE);
1904 if (xp_theme_draw (cr, xp_progress_bar, style, x, y,
1905 width, height, state_type))
1910 shadow_type = GTK_SHADOW_NONE;
1913 else if (detail && strcmp (detail, "menuitem") == 0)
1915 shadow_type = GTK_SHADOW_NONE;
1916 if (draw_menu_item (cr, widget, style,
1917 x, y, width, height, state_type))
1922 else if (detail && !strcmp (detail, "trough"))
1924 if (widget && GTK_IS_PROGRESS_BAR (widget))
1926 GtkProgressBar *progress_bar = GTK_PROGRESS_BAR (widget);
1927 XpThemeElement xp_progress_bar =
1928 map_gtk_progress_bar_to_xp (progress_bar, TRUE);
1930 (cr, xp_progress_bar, style, x, y, width, height,
1937 /* Blank in classic Windows */
1940 else if (widget && GTK_IS_SCROLLBAR (widget))
1942 gboolean is_vertical = GTK_IS_VSCROLLBAR (widget);
1944 if (xp_theme_draw (cr,
1946 ? XP_THEME_ELEMENT_TROUGH_V
1947 : XP_THEME_ELEMENT_TROUGH_H,
1948 style, x, y, width, height, state_type))
1958 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
1960 SetTextColor (dc, GetSysColor (COLOR_3DHILIGHT));
1961 SetBkColor (dc, GetSysColor (COLOR_BTNFACE));
1962 FillRect (dc, &rect, get_dither_brush ());
1964 release_window_dc (&dc_info);
1969 else if (widget && GTK_IS_SCALE (widget))
1971 gboolean is_vertical = GTK_IS_VSCALE (widget);
1973 if (!xp_theme_is_active ())
1975 parent_class->draw_box (style, cr, state_type,
1977 widget, detail, x, y, width, height);
1983 (cr, XP_THEME_ELEMENT_SCALE_TROUGH_V,
1984 style, (2 * x + width) / 2, y, 2, height,
1990 parent_class->draw_box (style, cr, state_type,
1991 GTK_SHADOW_ETCHED_IN,
1993 (2 * x + width) / 2, y, 1, height);
1998 (cr, XP_THEME_ELEMENT_SCALE_TROUGH_H,
1999 style, x, (2 * y + height) / 2, width, 2,
2005 parent_class->draw_box (style, cr, state_type,
2006 GTK_SHADOW_ETCHED_IN,
2008 (2 * y + height) / 2, width, 1);
2014 else if (detail && strcmp (detail, "optionmenu") == 0)
2016 if (xp_theme_draw (cr, XP_THEME_ELEMENT_EDIT_TEXT,
2017 style, x, y, width, height, state_type))
2023 && (strcmp (detail, "vscrollbar") == 0
2024 || strcmp (detail, "hscrollbar") == 0))
2029 && (strcmp (detail, "handlebox_bin") == 0
2030 || strcmp (detail, "toolbar") == 0
2031 || strcmp (detail, "menubar") == 0))
2033 if (xp_theme_draw (cr, XP_THEME_ELEMENT_REBAR,
2034 style, x, y, width, height, state_type))
2039 else if (detail && (!strcmp (detail, "handlebox"))) /* grip */
2041 if (!xp_theme_is_active ())
2046 else if (detail && !strcmp (detail, "notebook") && GTK_IS_NOTEBOOK (widget))
2048 if (xp_theme_draw (cr, XP_THEME_ELEMENT_TAB_PANE, style,
2049 x, y, width, height, state_type))
2057 const gchar *name = gtk_widget_get_name (widget);
2059 if (name && !strcmp (name, "gtk-tooltips"))
2062 (cr, XP_THEME_ELEMENT_TOOLTIP, style, x, y, width,
2063 height, state_type))
2074 hdc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
2076 brush = GetSysColorBrush (COLOR_3DDKSHADOW);
2080 FrameRect (hdc, &rect, brush);
2083 InflateRect (&rect, -1, -1);
2084 FillRect (hdc, &rect, (HBRUSH) (COLOR_INFOBK + 1));
2086 release_window_dc (&dc_info);
2093 parent_class->draw_box (style, cr, state_type, shadow_type,
2094 widget, detail, x, y, width, height);
2096 if (detail && strcmp (detail, "optionmenu") == 0)
2098 GtkRequisition indicator_size;
2099 GtkBorder indicator_spacing;
2102 option_menu_get_props (widget, &indicator_size, &indicator_spacing);
2104 if (gtk_widget_get_direction (widget) == GTK_TEXT_DIR_RTL)
2107 x + indicator_size.width + indicator_spacing.left +
2108 indicator_spacing.right;
2112 vline_x = x + width - (indicator_size.width +
2113 indicator_spacing.left +
2114 indicator_spacing.right) - style->xthickness;
2116 parent_class->draw_vline (style, cr, state_type, widget,
2118 y + style->ythickness + 1,
2119 y + height - style->ythickness - 3, vline_x);
2125 draw_tab (GtkStyle *style,
2128 GtkShadowType shadow,
2130 const gchar *detail, gint x, gint y, gint width, gint height)
2132 GtkRequisition indicator_size;
2133 GtkBorder indicator_spacing;
2137 g_return_if_fail (style != NULL);
2138 g_return_if_fail (cr != NULL);
2140 if (detail && !strcmp (detail, "optionmenutab"))
2142 GtkAllocation allocation;
2144 gtk_widget_get_allocation (widget, &allocation);
2145 if (xp_theme_draw (cr, XP_THEME_ELEMENT_COMBOBUTTON,
2146 style, x - 5, allocation.y + 1,
2147 width + 10, allocation.height - 2,
2154 option_menu_get_props (widget, &indicator_size, &indicator_spacing);
2156 x += (width - indicator_size.width) / 2;
2157 arrow_height = (indicator_size.width + 1) / 2;
2159 y += (height - arrow_height) / 2;
2161 draw_varrow (cr, &style->black, shadow, GTK_ARROW_DOWN,
2162 x, y, indicator_size.width, arrow_height);
2165 /* Draw classic Windows tab - thanks Mozilla!
2166 (no system API for this, but DrawEdge can draw all the parts of a tab) */
2168 DrawTab (HDC hdc, const RECT R, gint32 aPosition, gboolean aSelected,
2169 gboolean aDrawLeft, gboolean aDrawRight)
2171 gint32 leftFlag, topFlag, rightFlag, lightFlag, shadeFlag;
2172 RECT topRect, sideRect, bottomRect, lightRect, shadeRect;
2173 gint32 selectedOffset, lOffset, rOffset;
2175 selectedOffset = aSelected ? 1 : 0;
2176 lOffset = aDrawLeft ? 2 : 0;
2177 rOffset = aDrawRight ? 2 : 0;
2179 /* Get info for tab orientation/position (Left, Top, Right, Bottom) */
2185 rightFlag = BF_BOTTOM;
2186 lightFlag = BF_DIAGONAL_ENDTOPRIGHT;
2187 shadeFlag = BF_DIAGONAL_ENDBOTTOMRIGHT;
2189 SetRect (&topRect, R.left, R.top + lOffset, R.right,
2190 R.bottom - rOffset);
2191 SetRect (&sideRect, R.left + 2, R.top, R.right - 2 + selectedOffset,
2193 SetRect (&bottomRect, R.right - 2, R.top, R.right, R.bottom);
2194 SetRect (&lightRect, R.left, R.top, R.left + 3, R.top + 3);
2195 SetRect (&shadeRect, R.left + 1, R.bottom - 2, R.left + 2,
2202 rightFlag = BF_RIGHT;
2203 lightFlag = BF_DIAGONAL_ENDTOPRIGHT;
2204 shadeFlag = BF_DIAGONAL_ENDBOTTOMRIGHT;
2206 SetRect (&topRect, R.left + lOffset, R.top, R.right - rOffset,
2208 SetRect (&sideRect, R.left, R.top + 2, R.right,
2209 R.bottom - 1 + selectedOffset);
2210 SetRect (&bottomRect, R.left, R.bottom - 1, R.right, R.bottom);
2211 SetRect (&lightRect, R.left, R.top, R.left + 3, R.top + 3);
2212 SetRect (&shadeRect, R.right - 2, R.top + 1, R.right - 1, R.top + 2);
2218 rightFlag = BF_BOTTOM;
2219 lightFlag = BF_DIAGONAL_ENDTOPLEFT;
2220 shadeFlag = BF_DIAGONAL_ENDBOTTOMLEFT;
2222 SetRect (&topRect, R.left, R.top + lOffset, R.right,
2223 R.bottom - rOffset);
2224 SetRect (&sideRect, R.left + 2 - selectedOffset, R.top, R.right - 2,
2226 SetRect (&bottomRect, R.left, R.top, R.left + 2, R.bottom);
2227 SetRect (&lightRect, R.right - 3, R.top, R.right - 1, R.top + 2);
2228 SetRect (&shadeRect, R.right - 2, R.bottom - 3, R.right, R.bottom - 1);
2233 topFlag = BF_BOTTOM;
2234 rightFlag = BF_RIGHT;
2235 lightFlag = BF_DIAGONAL_ENDTOPLEFT;
2236 shadeFlag = BF_DIAGONAL_ENDBOTTOMLEFT;
2238 SetRect (&topRect, R.left + lOffset, R.top, R.right - rOffset,
2240 SetRect (&sideRect, R.left, R.top + 2 - selectedOffset, R.right,
2242 SetRect (&bottomRect, R.left, R.top, R.right, R.top + 2);
2243 SetRect (&lightRect, R.left, R.bottom - 3, R.left + 2, R.bottom - 1);
2244 SetRect (&shadeRect, R.right - 2, R.bottom - 3, R.right, R.bottom - 1);
2248 g_return_if_reached ();
2252 FillRect (hdc, &R, (HBRUSH) (COLOR_3DFACE + 1));
2255 DrawEdge (hdc, &topRect, EDGE_RAISED, BF_SOFT | topFlag);
2259 DrawEdge (hdc, &bottomRect, EDGE_RAISED, BF_SOFT | topFlag);
2267 DrawEdge (hdc, &sideRect, EDGE_RAISED, BF_SOFT | leftFlag | rightFlag);
2269 /* Tab Diagonal Corners */
2271 DrawEdge (hdc, &lightRect, EDGE_RAISED, BF_SOFT | lightFlag);
2274 DrawEdge (hdc, &shadeRect, EDGE_RAISED, BF_SOFT | shadeFlag);
2278 draw_themed_tab_button (GtkStyle *style,
2280 GtkStateType state_type,
2281 GtkNotebook *notebook,
2283 gint width, gint height, gint gap_side)
2286 GdkPixmap *pixmap = NULL;
2289 gtk_container_get_border_width (GTK_CONTAINER (notebook));
2290 GtkWidget *widget = GTK_WIDGET (notebook);
2291 GdkRectangle draw_rect;
2292 GdkPixbufRotation rotation = GDK_PIXBUF_ROTATE_NONE;
2293 GtkAllocation allocation;
2295 gtk_widget_get_allocation (widget, &allocation);
2297 if (gap_side == GTK_POS_TOP)
2301 if (state_type == GTK_STATE_NORMAL)
2305 draw_rect.width = width + 2;
2306 draw_rect.height = height;
2314 draw_rect.x = x + 2;
2316 draw_rect.width = width - 2;
2317 draw_rect.height = height - 2;
2320 /* If we are currently drawing the right-most tab, and if that tab is the selected tab... */
2321 widget_right = allocation.x + allocation.width - border_width - 2;
2323 if (draw_rect.x + draw_rect.width >= widget_right)
2325 draw_rect.width = widget_right - draw_rect.x;
2328 if (gap_side == GTK_POS_BOTTOM)
2332 if (state_type == GTK_STATE_NORMAL)
2336 draw_rect.width = width + 2;
2337 draw_rect.height = height;
2341 draw_rect.x = x + 2;
2342 draw_rect.y = y + 2;
2343 draw_rect.width = width - 2;
2344 draw_rect.height = height - 2;
2347 /* If we are currently drawing the right-most tab, and if that tab is the selected tab... */
2348 widget_right = allocation.x + allocation.width - border_width - 2;
2350 if (draw_rect.x + draw_rect.width >= widget_right)
2352 draw_rect.width = widget_right - draw_rect.x;
2355 rotation = GDK_PIXBUF_ROTATE_UPSIDEDOWN;
2357 else if (gap_side == GTK_POS_LEFT)
2361 if (state_type == GTK_STATE_NORMAL)
2365 draw_rect.width = width;
2366 draw_rect.height = height + 2;
2375 draw_rect.y = y + 2;
2376 draw_rect.width = width - 2;
2377 draw_rect.height = height - 2;
2380 /* If we are currently drawing the bottom-most tab, and if that tab is the selected tab... */
2381 widget_bottom = allocation.x + allocation.height - border_width - 2;
2383 if (draw_rect.y + draw_rect.height >= widget_bottom)
2385 draw_rect.height = widget_bottom - draw_rect.y;
2388 rotation = GDK_PIXBUF_ROTATE_COUNTERCLOCKWISE;
2390 else if (gap_side == GTK_POS_RIGHT)
2394 if (state_type == GTK_STATE_NORMAL)
2396 draw_rect.x = x + 1;
2398 draw_rect.width = width;
2399 draw_rect.height = height + 2;
2407 draw_rect.x = x + 2;
2408 draw_rect.y = y + 2;
2409 draw_rect.width = width - 2;
2410 draw_rect.height = height - 2;
2413 /* If we are currently drawing the bottom-most tab, and if that tab is the selected tab... */
2414 widget_bottom = allocation.x + allocation.height - border_width - 2;
2416 if (draw_rect.y + draw_rect.height >= widget_bottom)
2418 draw_rect.height = widget_bottom - draw_rect.y;
2421 rotation = GDK_PIXBUF_ROTATE_CLOCKWISE;
2424 if (gap_side == GTK_POS_TOP)
2426 if (!xp_theme_draw (cr, XP_THEME_ELEMENT_TAB_ITEM, style,
2427 draw_rect.x, draw_rect.y,
2428 draw_rect.width, draw_rect.height,
2441 if (gap_side == GTK_POS_LEFT || gap_side == GTK_POS_RIGHT)
2443 pixmap = gdk_pixmap_new (cr, draw_rect.height, draw_rect.width, -1);
2445 if (!xp_theme_draw (pixmap, XP_THEME_ELEMENT_TAB_ITEM, style,
2447 draw_rect.y - draw_rect.y, draw_rect.x - draw_rect.x,
2448 draw_rect.height, draw_rect.width, state_type, 0))
2450 g_object_unref (pixmap);
2454 pixbuf = gdk_pixbuf_get_from_drawable (NULL, pixmap, NULL, 0, 0, 0, 0,
2455 draw_rect.height, draw_rect.width);
2456 g_object_unref (pixmap);
2460 pixmap = gdk_pixmap_new (cr, draw_rect.width, draw_rect.height, -1);
2462 if (!xp_theme_draw (pixmap, XP_THEME_ELEMENT_TAB_ITEM, style,
2464 draw_rect.x - draw_rect.x, draw_rect.y - draw_rect.y,
2465 draw_rect.width, draw_rect.height, state_type, 0))
2467 g_object_unref (pixmap);
2471 pixbuf = gdk_pixbuf_get_from_drawable (NULL, pixmap, NULL, 0, 0, 0, 0,
2472 draw_rect.width, draw_rect.height);
2473 g_object_unref (pixmap);
2476 rotated = gdk_pixbuf_rotate_simple (pixbuf, rotation);
2477 g_object_unref (pixbuf);
2480 // XXX - This is really hacky and evil. When we're drawing the left-most tab
2481 // while it is active on a bottom-oriented notebook, there is one white
2482 // pixel at the top. There may be a better solution than this if someone
2483 // has time to discover it.
2484 if (gap_side == GTK_POS_BOTTOM && state_type == GTK_STATE_NORMAL
2485 && x == allocation.x)
2487 int rowstride = gdk_pixbuf_get_rowstride (pixbuf);
2488 int n_channels = gdk_pixbuf_get_n_channels (pixbuf);
2491 guchar *pixels = gdk_pixbuf_get_pixels (pixbuf);
2492 guchar *p = pixels + rowstride;
2494 for (psub = 0; psub < n_channels; psub++)
2496 pixels[psub] = p[psub];
2500 gdk_cairo_set_source_pixbuf (cr, pixbuf, clip_rect.x, clip_rect.y);
2502 g_object_unref (pixbuf);
2510 draw_tab_button (GtkStyle *style,
2512 GtkStateType state_type,
2513 GtkShadowType shadow_type,
2515 const gchar *detail,
2516 gint x, gint y, gint width, gint height, gint gap_side)
2518 if (gap_side == GTK_POS_TOP || gap_side == GTK_POS_BOTTOM)
2520 /* experimental tab-drawing code from mozilla */
2526 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
2528 if (gap_side == GTK_POS_TOP)
2530 else if (gap_side == GTK_POS_BOTTOM)
2531 aPosition = BF_BOTTOM;
2532 else if (gap_side == GTK_POS_LEFT)
2533 aPosition = BF_LEFT;
2535 aPosition = BF_RIGHT;
2537 if (state_type == GTK_STATE_PRELIGHT)
2538 state_type = GTK_STATE_NORMAL;
2541 gdk_cairo_set_source_color (cr, &style->dark[state_type]);
2544 DrawTab (dc, rect, aPosition,
2545 state_type != GTK_STATE_PRELIGHT,
2546 (gap_side != GTK_POS_LEFT), (gap_side != GTK_POS_RIGHT));
2548 release_window_dc (&dc_info);
2557 draw_extension (GtkStyle *style,
2559 GtkStateType state_type,
2560 GtkShadowType shadow_type,
2562 const gchar *detail,
2564 gint width, gint height, GtkPositionType gap_side)
2566 if (widget && GTK_IS_NOTEBOOK (widget) && detail && !strcmp (detail, "tab"))
2568 GtkNotebook *notebook = GTK_NOTEBOOK (widget);
2570 /* draw_themed_tab_button and draw_tab_button expect to work with tab
2571 * position, instead of simply taking the "side of the gap" (gap_side)
2572 * which simply said is the side of the tab that touches the notebook
2573 * frame and is always the exact opposite of the gap side... */
2574 int tab_pos = gtk_notebook_get_tab_pos (notebook);
2576 if (!draw_themed_tab_button (style, cr, state_type,
2578 width, height, tab_pos))
2580 if (!draw_tab_button (style, cr, state_type,
2581 shadow_type, widget,
2582 detail, x, y, width, height, tab_pos))
2584 /* GtkStyle expects the usual gap_side */
2585 parent_class->draw_extension (style, cr, state_type,
2586 shadow_type, widget, detail,
2587 x, y, width, height,
2595 draw_box_gap (GtkStyle *style, cairo_t *cr, GtkStateType state_type,
2596 GtkShadowType shadow_type,
2597 GtkWidget *widget, const gchar *detail, gint x,
2598 gint y, gint width, gint height, GtkPositionType gap_side,
2599 gint gap_x, gint gap_width)
2601 if (GTK_IS_NOTEBOOK (widget) && detail && !strcmp (detail, "notebook"))
2603 GtkNotebook *notebook = GTK_NOTEBOOK (widget);
2604 int side = gtk_notebook_get_tab_pos (notebook);
2605 int x2 = x, y2 = y, w2 = width, h2 = height;
2607 if (side == GTK_POS_TOP)
2610 y2 = y - gtk_notebook_get_tab_vborder (notebook);
2612 h2 = height + gtk_notebook_get_tab_vborder (notebook) * 2;
2614 else if (side == GTK_POS_BOTTOM)
2619 h2 = height + gtk_notebook_get_tab_vborder (notebook) * 2;
2621 else if (side == GTK_POS_LEFT)
2623 x2 = x - gtk_notebook_get_tab_hborder (notebook);
2625 w2 = width + gtk_notebook_get_tab_hborder (notebook);
2628 else if (side == GTK_POS_RIGHT)
2632 w2 = width + gtk_notebook_get_tab_hborder (notebook) * 2;
2636 if (xp_theme_draw (cr, XP_THEME_ELEMENT_TAB_PANE, style,
2637 x2, y2, w2, h2, state_type))
2643 parent_class->draw_box_gap (style, cr, state_type, shadow_type,
2644 widget, detail, x, y, width, height,
2645 gap_side, gap_x, gap_width);
2649 is_popup_window_child (GtkWidget *widget)
2652 GtkWindowType type = -1;
2654 top = gtk_widget_get_toplevel (widget);
2656 if (top && GTK_IS_WINDOW (top))
2658 g_object_get (top, "type", &type, NULL);
2660 if (type == GTK_WINDOW_POPUP)
2661 { /* Hack for combo boxes */
2670 draw_flat_box (GtkStyle *style, cairo_t *cr,
2671 GtkStateType state_type, GtkShadowType shadow_type,
2673 const gchar *detail, gint x, gint y, gint width, gint height)
2677 if (state_type == GTK_STATE_SELECTED &&
2678 (!strncmp ("cell_even", detail, 9) || !strncmp ("cell_odd", detail, 8)))
2680 GdkColor *gc = gtk_widget_has_focus (widget) ? &style->base[state_type] : &style->base[GTK_STATE_ACTIVE];
2682 _cairo_draw_rectangle (cr, gc, TRUE, x, y, width, height);
2686 else if (!strcmp (detail, "checkbutton"))
2688 if (state_type == GTK_STATE_PRELIGHT)
2695 parent_class->draw_flat_box (style, cr, state_type, shadow_type,
2696 widget, detail, x, y, width, height);
2700 draw_menu_border (cairo_t *cr, GtkStyle *style,
2701 gint x, gint y, gint width, gint height)
2707 dc = get_window_dc (style, cr, GTK_STATE_NORMAL, &dc_info, x, y, width, height, &rect);
2712 if (xp_theme_is_active ())
2714 FrameRect (dc, &rect, GetSysColorBrush (COLOR_3DSHADOW));
2718 DrawEdge (dc, &rect, EDGE_RAISED, BF_RECT);
2721 release_window_dc (&dc_info);
2727 draw_shadow (GtkStyle *style,
2729 GtkStateType state_type,
2730 GtkShadowType shadow_type,
2732 const gchar *detail, gint x, gint y, gint width, gint height)
2734 gboolean is_handlebox;
2735 gboolean is_toolbar;
2737 if (detail && !strcmp (detail, "frame"))
2746 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
2747 if (is_combo_box_child (widget))
2749 FillRect (dc, &rect, GetSysColorBrush (COLOR_WINDOW));
2751 else if (is_popup_window_child (widget))
2753 FrameRect (dc, &rect, GetSysColorBrush (COLOR_WINDOWFRAME));
2757 switch (shadow_type)
2760 draw_3d_border (dc, &rect, TRUE);
2763 case GTK_SHADOW_OUT:
2764 draw_3d_border (dc, &rect, FALSE);
2767 case GTK_SHADOW_ETCHED_IN:
2768 draw_3d_border (dc, &rect, TRUE);
2769 InflateRect (&rect, -1, -1);
2770 draw_3d_border (dc, &rect, FALSE);
2773 case GTK_SHADOW_ETCHED_OUT:
2774 draw_3d_border (dc, &rect, FALSE);
2775 InflateRect (&rect, -1, -1);
2776 draw_3d_border (dc, &rect, TRUE);
2779 case GTK_SHADOW_NONE:
2784 release_window_dc (&dc_info);
2788 if (detail && (!strcmp (detail, "entry") || !strcmp (detail, "combobox")))
2790 if (shadow_type != GTK_SHADOW_IN)
2793 if (!xp_theme_draw (cr, XP_THEME_ELEMENT_EDIT_TEXT, style,
2794 x, y, width, height, state_type))
2800 dc = get_window_dc (style, cr, state_type, &dc_info,
2801 x, y, width, height, &rect);
2803 DrawEdge (dc, &rect, EDGE_SUNKEN, BF_RECT);
2804 release_window_dc (&dc_info);
2810 if (detail && !strcmp (detail, "scrolled_window") &&
2811 xp_theme_draw (cr, XP_THEME_ELEMENT_EDIT_TEXT, style,
2812 x, y, width, height, state_type))
2817 if (detail && !strcmp (detail, "spinbutton"))
2820 if (detail && !strcmp (detail, "menu"))
2822 if (draw_menu_border (cr, style, x, y, width, height))
2828 if (detail && !strcmp (detail, "handlebox"))
2831 is_handlebox = (detail && !strcmp (detail, "handlebox_bin"));
2832 is_toolbar = (detail
2833 && (!strcmp (detail, "toolbar")
2834 || !strcmp (detail, "menubar")));
2836 if (is_toolbar || is_handlebox)
2838 if (shadow_type == GTK_SHADOW_NONE)
2848 HGDIOBJ old_pen = NULL;
2849 GtkPositionType pos;
2853 pos = gtk_handle_box_get_handle_position (GTK_HANDLE_BOX (widget));
2855 If the handle box is at left side,
2856 we shouldn't draw its right border.
2857 The same holds true for top, right, and bottom.
2862 pos = GTK_POS_RIGHT;
2870 pos = GTK_POS_BOTTOM;
2873 case GTK_POS_BOTTOM:
2880 GtkWidget *parent = gtk_widget_get_parent (widget);
2882 /* Dirty hack for toolbars contained in handle boxes */
2883 if (GTK_IS_HANDLE_BOX (parent))
2885 pos = gtk_handle_box_get_handle_position (GTK_HANDLE_BOX (parent));
2891 Make pos != all legal enum vaules of GtkPositionType.
2892 So every border will be draw.
2894 pos = (GtkPositionType) - 1;
2898 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
2900 if (pos != GTK_POS_LEFT)
2902 old_pen = SelectObject (dc, get_light_pen ());
2903 MoveToEx (dc, rect.left, rect.top, NULL);
2904 LineTo (dc, rect.left, rect.bottom);
2906 if (pos != GTK_POS_TOP)
2908 old_pen = SelectObject (dc, get_light_pen ());
2909 MoveToEx (dc, rect.left, rect.top, NULL);
2910 LineTo (dc, rect.right, rect.top);
2912 if (pos != GTK_POS_RIGHT)
2914 old_pen = SelectObject (dc, get_dark_pen ());
2915 MoveToEx (dc, rect.right - 1, rect.top, NULL);
2916 LineTo (dc, rect.right - 1, rect.bottom);
2918 if (pos != GTK_POS_BOTTOM)
2920 old_pen = SelectObject (dc, get_dark_pen ());
2921 MoveToEx (dc, rect.left, rect.bottom - 1, NULL);
2922 LineTo (dc, rect.right, rect.bottom - 1);
2925 SelectObject (dc, old_pen);
2926 release_window_dc (&dc_info);
2932 if (detail && !strcmp (detail, "statusbar"))
2937 parent_class->draw_shadow (style, cr, state_type, shadow_type,
2938 widget, detail, x, y, width, height);
2942 draw_hline (GtkStyle *style,
2944 GtkStateType state_type,
2946 const gchar *detail, gint x1, gint x2, gint y)
2948 if (xp_theme_is_active () && detail && !strcmp (detail, "menuitem"))
2951 gint new_y, new_height;
2954 xp_theme_get_element_dimensions (XP_THEME_ELEMENT_MENU_SEPARATOR,
2958 /* Center the separator */
2959 y_offset = (cy / 2) - 1;
2960 new_y = (y - y_offset) >= 0 ? y - y_offset : y;
2964 (cr, XP_THEME_ELEMENT_MENU_SEPARATOR, style, x1, new_y, x2, new_height,
2971 _cairo_draw_line (cr, &style->dark[state_type], x1, y, x2, y);
2977 if (style->ythickness == 2)
2979 _cairo_draw_line (cr, &style->dark[state_type], x1, y, x2, y);
2981 _cairo_draw_line (cr, &style->light[state_type], x1, y, x2, y);
2986 parent_class->draw_hline (style, cr, state_type, widget,
2993 draw_vline (GtkStyle *style,
2995 GtkStateType state_type,
2997 const gchar *detail, gint y1, gint y2, gint x)
2999 if (style->xthickness == 2)
3001 _cairo_draw_line (cr, &style->dark[state_type], x, y1, x, y2);
3003 _cairo_draw_line (cr, &style->light[state_type], x, y1, x, y2);
3008 parent_class->draw_vline (style, cr, state_type, widget,
3014 draw_slider (GtkStyle *style,
3016 GtkStateType state_type,
3017 GtkShadowType shadow_type,
3019 const gchar *detail,
3021 gint y, gint width, gint height, GtkOrientation orientation)
3023 if (GTK_IS_SCALE (widget) &&
3024 xp_theme_draw (cr, ((orientation == GTK_ORIENTATION_VERTICAL) ?
3025 XP_THEME_ELEMENT_SCALE_SLIDER_V :
3026 XP_THEME_ELEMENT_SCALE_SLIDER_H), style, x, y, width,
3027 height, state_type))
3032 parent_class->draw_slider (style, cr, state_type, shadow_type,
3033 widget, detail, x, y, width, height,
3038 draw_resize_grip (GtkStyle *style,
3040 GtkStateType state_type,
3042 const gchar *detail,
3043 GdkWindowEdge edge, gint x, gint y, gint width, gint height)
3045 if (detail && !strcmp (detail, "statusbar"))
3048 (cr, XP_THEME_ELEMENT_STATUS_GRIPPER, style, x, y, width,
3049 height, state_type))
3057 HDC dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
3060 gdk_cairo_set_source_color (cr, &style->dark[state_type]);
3063 DrawFrameControl (dc, &rect, DFC_SCROLL, DFCS_SCROLLSIZEGRIP);
3064 release_window_dc (&dc_info);
3070 parent_class->draw_resize_grip (style, cr, state_type,
3071 widget, detail, edge, x, y, width, height);
3075 draw_handle (GtkStyle *style,
3077 GtkStateType state_type,
3078 GtkShadowType shadow_type,
3080 const gchar *detail,
3082 gint y, gint width, gint height, GtkOrientation orientation)
3088 if (is_toolbar_child (widget))
3090 XpThemeElement hndl;
3092 if (GTK_IS_HANDLE_BOX (widget))
3094 GtkPositionType pos;
3095 pos = gtk_handle_box_get_handle_position (GTK_HANDLE_BOX (widget));
3097 if (pos == GTK_POS_TOP || pos == GTK_POS_BOTTOM)
3099 orientation = GTK_ORIENTATION_HORIZONTAL;
3103 orientation = GTK_ORIENTATION_VERTICAL;
3107 if (orientation == GTK_ORIENTATION_VERTICAL)
3108 hndl = XP_THEME_ELEMENT_REBAR_GRIPPER_V;
3110 hndl = XP_THEME_ELEMENT_REBAR_GRIPPER_H;
3112 if (xp_theme_draw (cr, hndl, style, x, y, width, height,
3118 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
3120 if (orientation == GTK_ORIENTATION_VERTICAL)
3123 rect.right = rect.left + 3;
3130 rect.bottom = rect.top + 3;
3135 draw_3d_border (dc, &rect, FALSE);
3136 release_window_dc (&dc_info);
3140 if (!GTK_IS_PANED (widget))
3142 gint xthick, ythick;
3143 GdkColor *light, *dark, *shadow;
3146 gtk_paint_box (style, cr, state_type, shadow_type,
3147 widget, detail, x, y, width, height);
3149 light = &style->light[state_type];
3150 dark = &style->dark[state_type];
3151 shadow = &style->mid[state_type];
3153 xthick = style->xthickness;
3154 ythick = style->ythickness;
3156 dest.x = x + xthick;
3157 dest.y = y + ythick;
3158 dest.width = width - (xthick * 2);
3159 dest.height = height - (ythick * 2);
3161 if (dest.width < dest.height)
3166 if (dest.width < dest.height)
3168 _cairo_draw_line (cr, light, dest.x, dest.y, dest.x,
3170 _cairo_draw_line (cr, dark, dest.x + (dest.width / 2),
3171 dest.y, dest.x + (dest.width / 2), dest.height);
3172 _cairo_draw_line (cr, shadow, dest.x + dest.width,
3173 dest.y, dest.x + dest.width, dest.height);
3177 _cairo_draw_line (cr, light, dest.x, dest.y,
3178 dest.x + dest.width, dest.y);
3179 _cairo_draw_line (cr, dark, dest.x,
3180 dest.y + (dest.height / 2),
3181 dest.x + dest.width, dest.y + (dest.height / 2));
3182 _cairo_draw_line (cr, shadow, dest.x,
3183 dest.y + dest.height, dest.x + dest.width,
3184 dest.y + dest.height);
3190 draw_focus (GtkStyle *style,
3192 GtkStateType state_type,
3194 const gchar *detail, gint x, gint y, gint width, gint height)
3200 if (!gtk_widget_get_can_focus (widget))
3205 if (is_combo_box_child (widget)
3206 && (GTK_IS_ARROW (widget) || GTK_IS_BUTTON (widget)))
3210 if (GTK_IS_TREE_VIEW (gtk_widget_get_parent (widget)) /* list view bheader */)
3215 dc = get_window_dc (style, cr, state_type, &dc_info, x, y, width, height, &rect);
3216 DrawFocusRect (dc, &rect);
3217 release_window_dc (&dc_info);
3219 parent_class->draw_focus (style, cr, state_type,
3220 widget, detail, x, y, width, height);
3225 draw_layout (GtkStyle *style,
3227 GtkStateType state_type,
3230 const gchar *detail,
3231 gint old_x, gint old_y, PangoLayout *layout)
3233 GtkNotebook *notebook = NULL;
3237 /* In the XP theme, labels don't appear correctly centered inside
3238 * notebook tabs, so we give them a gentle nudge two pixels to the
3239 * right. A little hackish, but what are 'ya gonna do? -- Cody
3241 if (xp_theme_is_active () && detail && !strcmp (detail, "label"))
3243 if (gtk_widget_get_parent (widget) != NULL)
3245 if (GTK_IS_NOTEBOOK (gtk_widget_get_parent (widget)))
3248 notebook = GTK_NOTEBOOK (gtk_widget_get_parent (widget));
3249 side = gtk_notebook_get_tab_pos (notebook);
3251 if (side == GTK_POS_TOP || side == GTK_POS_BOTTOM)
3259 parent_class->draw_layout (style, cr, state_type,
3260 use_text, widget, detail, x, y, layout);
3264 msw_style_init_from_rc (GtkStyle *style, GtkRcStyle *rc_style)
3266 setup_system_font (style);
3267 setup_menu_settings (gtk_settings_get_default ());
3268 setup_system_styles (style);
3269 parent_class->init_from_rc (style, rc_style);
3273 msw_style_class_init (MswStyleClass *klass)
3275 GtkStyleClass *style_class = GTK_STYLE_CLASS (klass);
3277 parent_class = g_type_class_peek_parent (klass);
3279 style_class->init_from_rc = msw_style_init_from_rc;
3280 style_class->draw_arrow = draw_arrow;
3281 style_class->draw_box = draw_box;
3282 style_class->draw_check = draw_check;
3283 style_class->draw_option = draw_option;
3284 style_class->draw_tab = draw_tab;
3285 style_class->draw_flat_box = draw_flat_box;
3286 style_class->draw_expander = draw_expander;
3287 style_class->draw_extension = draw_extension;
3288 style_class->draw_box_gap = draw_box_gap;
3289 style_class->draw_shadow = draw_shadow;
3290 style_class->draw_hline = draw_hline;
3291 style_class->draw_vline = draw_vline;
3292 style_class->draw_handle = draw_handle;
3293 style_class->draw_resize_grip = draw_resize_grip;
3294 style_class->draw_slider = draw_slider;
3295 style_class->draw_focus = draw_focus;
3296 style_class->draw_layout = draw_layout;
3299 GType msw_type_style = 0;
3302 msw_style_register_type (GTypeModule *module)
3304 const GTypeInfo object_info = {
3305 sizeof (MswStyleClass),
3306 (GBaseInitFunc) NULL,
3307 (GBaseFinalizeFunc) NULL,
3308 (GClassInitFunc) msw_style_class_init,
3309 NULL, /* class_finalize */
3310 NULL, /* class_data */
3312 0, /* n_preallocs */
3313 (GInstanceInitFunc) NULL,
3316 msw_type_style = g_type_module_register_type (module,
3318 "MswStyle", &object_info, 0);
3322 msw_style_init (void)
3325 msw_style_setup_system_settings ();
3326 setup_msw_rc_style ();
3330 DeleteObject (g_light_pen);
3336 DeleteObject (g_dark_pen);
3342 msw_style_finalize (void)
3346 DeleteObject (g_dither_brush);
3351 DeleteObject (g_light_pen);
3356 DeleteObject (g_dark_pen);