1 /* GDK - The GIMP Drawing Kit
2 * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
3 * Copyright (C) 1998-2004 Tor Lillqvist
4 * Copyright (C) 2001-2009 Hans Breuer
5 * Copyright (C) 2007-2009 Cody Russell
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the
19 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20 * Boston, MA 02111-1307, USA.
24 * Modified by the GTK+ Team and others 1997-2000. See the AUTHORS
25 * file for a list of people on the GTK+ Team. See the ChangeLog
26 * files for a list of changes. These files are distributed with
27 * GTK+ at ftp://ftp.gtk.org/pub/gtk/.
34 #include "gdkwindowimpl.h"
35 #include "gdkprivate-win32.h"
36 #include "gdkdeviceprivate.h"
37 #include "gdkdevicemanager-win32.h"
38 #include "gdkenumtypes.h"
40 static GdkColormap* gdk_window_impl_win32_get_colormap (GdkDrawable *drawable);
41 static void gdk_window_impl_win32_set_colormap (GdkDrawable *drawable,
43 static void gdk_window_impl_win32_init (GdkWindowImplWin32 *window);
44 static void gdk_window_impl_win32_class_init (GdkWindowImplWin32Class *klass);
45 static void gdk_window_impl_win32_finalize (GObject *object);
47 static gpointer parent_class = NULL;
48 static GSList *modal_window_stack = NULL;
50 static void update_style_bits (GdkWindow *window);
51 static gboolean _gdk_window_get_functions (GdkWindow *window,
52 GdkWMFunction *functions);
54 #define WINDOW_IS_TOPLEVEL(window) \
55 (GDK_WINDOW_TYPE (window) != GDK_WINDOW_CHILD && \
56 GDK_WINDOW_TYPE (window) != GDK_WINDOW_FOREIGN && \
57 GDK_WINDOW_TYPE (window) != GDK_WINDOW_OFFSCREEN)
59 static void gdk_window_impl_iface_init (GdkWindowImplIface *iface);
62 GDK_WINDOW_SCREEN (GObject *win)
68 _gdk_window_impl_win32_get_type (void)
70 static GType object_type = 0;
74 const GTypeInfo object_info =
76 sizeof (GdkWindowImplWin32Class),
78 (GBaseFinalizeFunc) NULL,
79 (GClassInitFunc) gdk_window_impl_win32_class_init,
80 NULL, /* class_finalize */
81 NULL, /* class_data */
82 sizeof (GdkWindowImplWin32),
84 (GInstanceInitFunc) gdk_window_impl_win32_init,
87 const GInterfaceInfo window_impl_info =
89 (GInterfaceInitFunc) gdk_window_impl_iface_init,
94 object_type = g_type_register_static (GDK_TYPE_DRAWABLE_IMPL_WIN32,
97 g_type_add_interface_static (object_type,
106 _gdk_window_impl_get_type (void)
108 return _gdk_window_impl_win32_get_type ();
112 gdk_window_impl_win32_init (GdkWindowImplWin32 *impl)
114 impl->toplevel_window_type = -1;
115 impl->hcursor = NULL;
116 impl->hicon_big = NULL;
117 impl->hicon_small = NULL;
118 impl->hint_flags = 0;
119 impl->type_hint = GDK_WINDOW_TYPE_HINT_NORMAL;
120 impl->extension_events_selected = FALSE;
121 impl->transient_owner = NULL;
122 impl->transient_children = NULL;
123 impl->num_transients = 0;
124 impl->changing_state = FALSE;
128 gdk_window_impl_win32_class_init (GdkWindowImplWin32Class *klass)
130 GObjectClass *object_class = G_OBJECT_CLASS (klass);
131 GdkDrawableClass *drawable_class = GDK_DRAWABLE_CLASS (klass);
133 parent_class = g_type_class_peek_parent (klass);
135 object_class->finalize = gdk_window_impl_win32_finalize;
137 drawable_class->set_colormap = gdk_window_impl_win32_set_colormap;
138 drawable_class->get_colormap = gdk_window_impl_win32_get_colormap;
142 gdk_window_impl_win32_finalize (GObject *object)
144 GdkWindowObject *wrapper;
145 GdkDrawableImplWin32 *draw_impl;
146 GdkWindowImplWin32 *window_impl;
148 g_return_if_fail (GDK_IS_WINDOW_IMPL_WIN32 (object));
150 draw_impl = GDK_DRAWABLE_IMPL_WIN32 (object);
151 window_impl = GDK_WINDOW_IMPL_WIN32 (object);
153 wrapper = (GdkWindowObject*) draw_impl->wrapper;
155 if (!GDK_WINDOW_DESTROYED (wrapper))
157 gdk_win32_handle_table_remove (draw_impl->handle);
160 if (window_impl->hcursor != NULL)
162 if (GetCursor () == window_impl->hcursor)
165 GDI_CALL (DestroyCursor, (window_impl->hcursor));
166 window_impl->hcursor = NULL;
169 if (window_impl->hicon_big != NULL)
171 GDI_CALL (DestroyIcon, (window_impl->hicon_big));
172 window_impl->hicon_big = NULL;
175 if (window_impl->hicon_small != NULL)
177 GDI_CALL (DestroyIcon, (window_impl->hicon_small));
178 window_impl->hicon_small = NULL;
181 G_OBJECT_CLASS (parent_class)->finalize (object);
185 _gdk_win32_adjust_client_rect (GdkWindow *window,
190 style = GetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE);
191 exstyle = GetWindowLong (GDK_WINDOW_HWND (window), GWL_EXSTYLE);
192 API_CALL (AdjustWindowRectEx, (rect, style, FALSE, exstyle));
196 gdk_window_impl_win32_get_colormap (GdkDrawable *drawable)
198 GdkDrawableImplWin32 *drawable_impl;
200 g_return_val_if_fail (GDK_IS_WINDOW_IMPL_WIN32 (drawable), NULL);
202 drawable_impl = GDK_DRAWABLE_IMPL_WIN32 (drawable);
204 if (!((GdkWindowObject *) drawable_impl->wrapper)->input_only &&
205 drawable_impl->colormap == NULL)
207 drawable_impl->colormap = gdk_screen_get_system_colormap (_gdk_screen);
208 g_object_ref (drawable_impl->colormap);
211 return drawable_impl->colormap;
215 gdk_window_impl_win32_set_colormap (GdkDrawable *drawable,
218 GdkWindowImplWin32 *impl;
219 GdkDrawableImplWin32 *draw_impl;
221 g_return_if_fail (GDK_IS_WINDOW_IMPL_WIN32 (drawable));
223 impl = GDK_WINDOW_IMPL_WIN32 (drawable);
224 draw_impl = GDK_DRAWABLE_IMPL_WIN32 (drawable);
227 GDK_DRAWABLE_CLASS (parent_class)->set_colormap (drawable, cmap);
232 g_print ("gdk_window_impl_win32_set_colormap: XXX\n");
237 _gdk_root_window_size_init (void)
239 GdkWindowObject *window_object;
243 window_object = GDK_WINDOW_OBJECT (_gdk_root);
244 rect = _gdk_monitors[0].rect;
245 for (i = 1; i < _gdk_num_monitors; i++)
246 gdk_rectangle_union (&rect, &_gdk_monitors[i].rect, &rect);
248 window_object->width = rect.width;
249 window_object->height = rect.height;
253 _gdk_windowing_window_init (GdkScreen *screen)
255 GdkWindowObject *private;
256 GdkDrawableImplWin32 *draw_impl;
258 g_assert (_gdk_root == NULL);
260 _gdk_root = g_object_new (GDK_TYPE_WINDOW, NULL);
261 private = (GdkWindowObject *)_gdk_root;
262 private->impl = g_object_new (_gdk_window_impl_get_type (), NULL);
263 private->impl_window = private;
265 draw_impl = GDK_DRAWABLE_IMPL_WIN32 (private->impl);
267 draw_impl->handle = GetDesktopWindow ();
268 draw_impl->wrapper = GDK_DRAWABLE (private);
269 draw_impl->colormap = gdk_screen_get_default_colormap (_gdk_screen);
270 g_object_ref (draw_impl->colormap);
272 private->window_type = GDK_WINDOW_ROOT;
273 private->depth = gdk_visual_get_system ()->depth;
275 _gdk_root_window_size_init ();
281 /* width and height already initialised in _gdk_root_window_size_init() */
282 private->viewable = TRUE;
284 gdk_win32_handle_table_insert ((HANDLE *) &draw_impl->handle, _gdk_root);
286 GDK_NOTE (MISC, g_print ("_gdk_root=%p\n", GDK_WINDOW_HWND (_gdk_root)));
290 get_default_title (void)
293 title = g_get_application_name ();
295 title = g_get_prgname ();
301 * is a wrapper function for RegisterWindowClassEx.
302 * It creates at least one unique class for every
303 * GdkWindowType. If support for single window-specific icons
304 * is ever needed (e.g Dialog specific), every such window should
308 RegisterGdkClass (GdkWindowType wtype, GdkWindowTypeHint wtype_hint)
310 static ATOM klassTOPLEVEL = 0;
311 static ATOM klassDIALOG = 0;
312 static ATOM klassCHILD = 0;
313 static ATOM klassTEMP = 0;
314 static ATOM klassTEMPSHADOW = 0;
315 static HICON hAppIcon = NULL;
316 static HICON hAppIconSm = NULL;
317 static WNDCLASSEXW wcl;
320 wcl.cbSize = sizeof (WNDCLASSEX);
321 wcl.style = 0; /* DON'T set CS_<H,V>REDRAW. It causes total redraw
322 * on WM_SIZE and WM_MOVE. Flicker, Performance!
324 wcl.lpfnWndProc = _gdk_win32_window_procedure;
327 wcl.hInstance = _gdk_app_hmodule;
331 /* initialize once! */
332 if (0 == hAppIcon && 0 == hAppIconSm)
334 gchar sLoc [MAX_PATH+1];
336 if (0 != GetModuleFileName (_gdk_app_hmodule, sLoc, MAX_PATH))
338 ExtractIconEx (sLoc, 0, &hAppIcon, &hAppIconSm, 1);
340 if (0 == hAppIcon && 0 == hAppIconSm)
342 if (0 != GetModuleFileName (_gdk_dll_hinstance, sLoc, MAX_PATH))
344 ExtractIconEx (sLoc, 0, &hAppIcon, &hAppIconSm, 1);
349 if (0 == hAppIcon && 0 == hAppIconSm)
351 hAppIcon = LoadImage (NULL, IDI_APPLICATION, IMAGE_ICON,
352 GetSystemMetrics (SM_CXICON),
353 GetSystemMetrics (SM_CYICON), 0);
354 hAppIconSm = LoadImage (NULL, IDI_APPLICATION, IMAGE_ICON,
355 GetSystemMetrics (SM_CXSMICON),
356 GetSystemMetrics (SM_CYSMICON), 0);
361 hAppIcon = hAppIconSm;
362 else if (0 == hAppIconSm)
363 hAppIconSm = hAppIcon;
365 wcl.lpszMenuName = NULL;
367 /* initialize once per class */
369 * HB: Setting the background brush leads to flicker, because we
370 * don't get asked how to clear the background. This is not what
371 * we want, at least not for input_only windows ...
373 #define ONCE_PER_CLASS() \
374 wcl.hIcon = CopyIcon (hAppIcon); \
375 wcl.hIconSm = CopyIcon (hAppIconSm); \
376 wcl.hbrBackground = NULL; \
377 wcl.hCursor = LoadCursor (NULL, IDC_ARROW);
381 case GDK_WINDOW_TOPLEVEL:
382 if (0 == klassTOPLEVEL)
384 wcl.lpszClassName = L"gdkWindowToplevel";
387 klassTOPLEVEL = RegisterClassExW (&wcl);
389 klass = klassTOPLEVEL;
392 case GDK_WINDOW_CHILD:
395 wcl.lpszClassName = L"gdkWindowChild";
397 wcl.style |= CS_PARENTDC; /* MSDN: ... enhances system performance. */
399 klassCHILD = RegisterClassExW (&wcl);
404 case GDK_WINDOW_DIALOG:
405 if (0 == klassDIALOG)
407 wcl.lpszClassName = L"gdkWindowDialog";
408 wcl.style |= CS_SAVEBITS;
410 klassDIALOG = RegisterClassExW (&wcl);
415 case GDK_WINDOW_TEMP:
416 if ((wtype_hint == GDK_WINDOW_TYPE_HINT_MENU) ||
417 (wtype_hint == GDK_WINDOW_TYPE_HINT_DROPDOWN_MENU) ||
418 (wtype_hint == GDK_WINDOW_TYPE_HINT_POPUP_MENU) ||
419 (wtype_hint == GDK_WINDOW_TYPE_HINT_TOOLTIP))
421 if (klassTEMPSHADOW == 0)
423 wcl.lpszClassName = L"gdkWindowTempShadow";
424 wcl.style |= CS_SAVEBITS;
425 if (LOBYTE (g_win32_get_windows_version()) > 0x05 ||
426 LOWORD (g_win32_get_windows_version()) == 0x0105)
428 /* Windows XP (5.1) or above */
429 wcl.style |= 0x00020000; /* CS_DROPSHADOW */
432 klassTEMPSHADOW = RegisterClassExW (&wcl);
435 klass = klassTEMPSHADOW;
441 wcl.lpszClassName = L"gdkWindowTemp";
442 wcl.style |= CS_SAVEBITS;
444 klassTEMP = RegisterClassExW (&wcl);
452 g_assert_not_reached ();
458 WIN32_API_FAILED ("RegisterClassExW");
459 g_error ("That is a fatal error");
465 _gdk_window_impl_new (GdkWindow *window,
466 GdkWindow *real_parent,
469 GdkEventMask event_mask,
470 GdkWindowAttr *attributes,
471 gint attributes_mask)
476 DWORD dwStyle = 0, dwExStyle;
478 GdkWindow *orig_parent;
479 GdkWindowObject *private;
480 GdkWindowImplWin32 *impl;
481 GdkDrawableImplWin32 *draw_impl;
484 gint window_width, window_height;
485 gint offset_x = 0, offset_y = 0;
487 private = (GdkWindowObject *)window;
489 orig_parent = real_parent;
492 g_print ("_gdk_window_impl_new: %s\n",
493 (attributes->window_type == GDK_WINDOW_TOPLEVEL ? "TOPLEVEL" :
494 (attributes->window_type == GDK_WINDOW_CHILD ? "CHILD" :
495 (attributes->window_type == GDK_WINDOW_DIALOG ? "DIALOG" :
496 (attributes->window_type == GDK_WINDOW_TEMP ? "TEMP" :
499 hparent = GDK_WINDOW_HWND (real_parent);
501 impl = g_object_new (_gdk_window_impl_get_type (), NULL);
502 private->impl = (GdkDrawable *)impl;
503 draw_impl = GDK_DRAWABLE_IMPL_WIN32 (impl);
504 draw_impl->wrapper = GDK_DRAWABLE (window);
506 // XXX: xattributes_mask = 0
509 if (attributes_mask & GDK_WA_VISUAL)
510 visual = attributes->visual;
512 visual = gdk_visual_get_system ();
516 impl->width = (attributes->width > 1) ? (attributes->width) : (1);
517 impl->height = (attributes->height > 1) ? (attributes->height) : (1);
519 impl->extension_events_selected = FALSE;
522 if (attributes->wclass == GDK_INPUT_OUTPUT)
526 private->input_only = FALSE;
527 private->depth = visual->depth;
529 if (attributes_mask & GDK_WA_COLORMAP)
531 draw_impl->colormap = attributes->colormap;
532 g_object_ref (attributes->colormap);
536 draw_impl->colormap = gdk_screen_get_system_colormap (_gdk_screen);
537 g_object_ref (draw_impl->colormap);
542 /* I very much doubt using WS_EX_TRANSPARENT actually
543 * corresponds to how X11 InputOnly windows work, but it appears
544 * to work well enough for the actual use cases in gtk.
546 dwExStyle = WS_EX_TRANSPARENT;
548 private->input_only = TRUE;
549 draw_impl->colormap = gdk_screen_get_system_colormap (_gdk_screen);
550 g_object_ref (draw_impl->colormap);
551 GDK_NOTE (MISC, g_print ("... GDK_INPUT_ONLY, system colormap\n"));
554 switch (private->window_type)
556 case GDK_WINDOW_TOPLEVEL:
557 case GDK_WINDOW_DIALOG:
558 if (GDK_WINDOW_TYPE (private->parent) != GDK_WINDOW_ROOT)
560 /* The common code warns for this case. */
561 hparent = GetDesktopWindow ();
563 /* Children of foreign windows aren't toplevel windows */
564 if (GDK_WINDOW_TYPE (orig_parent) == GDK_WINDOW_FOREIGN)
566 dwStyle = WS_CHILDWINDOW | WS_CLIPCHILDREN;
570 if (private->window_type == GDK_WINDOW_TOPLEVEL)
571 dwStyle = WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN;
573 dwStyle = WS_OVERLAPPED | WS_MINIMIZEBOX | WS_SYSMENU | WS_CAPTION | WS_THICKFRAME | WS_CLIPCHILDREN;
575 offset_x = _gdk_offset_x;
576 offset_y = _gdk_offset_y;
580 case GDK_WINDOW_CHILD:
581 dwStyle = WS_CHILDWINDOW | WS_CLIPCHILDREN | WS_CLIPSIBLINGS;
584 case GDK_WINDOW_TEMP:
585 /* A temp window is not necessarily a top level window */
586 dwStyle = (_gdk_root == real_parent ? WS_POPUP : WS_CHILDWINDOW);
587 dwStyle |= WS_CLIPCHILDREN | WS_CLIPSIBLINGS;
588 dwExStyle |= WS_EX_TOOLWINDOW;
589 offset_x = _gdk_offset_x;
590 offset_y = _gdk_offset_y;
594 g_assert_not_reached ();
597 if (private->window_type != GDK_WINDOW_CHILD)
599 rect.left = rect.top = 0;
600 rect.right = private->width;
601 rect.bottom = private->height;
603 AdjustWindowRectEx (&rect, dwStyle, FALSE, dwExStyle);
605 window_width = rect.right - rect.left;
606 window_height = rect.bottom - rect.top;
610 window_width = private->width;
611 window_height = private->height;
614 if (attributes_mask & GDK_WA_TITLE)
615 title = attributes->title;
617 title = get_default_title ();
618 if (!title || !*title)
621 private->event_mask = GDK_STRUCTURE_MASK | attributes->event_mask;
623 if (attributes_mask & GDK_WA_TYPE_HINT)
624 impl->type_hint = attributes->type_hint;
626 impl->type_hint = GDK_WINDOW_TYPE_HINT_NORMAL;
628 if (impl->type_hint == GDK_WINDOW_TYPE_HINT_UTILITY)
629 dwExStyle |= WS_EX_TOOLWINDOW;
632 private->parent->children = g_list_prepend (private->parent->children, window);
634 klass = RegisterGdkClass (private->window_type, impl->type_hint);
636 wtitle = g_utf8_to_utf16 (title, -1, NULL, NULL, NULL);
638 hwndNew = CreateWindowExW (dwExStyle,
639 MAKEINTRESOURCEW (klass),
642 ((attributes_mask & GDK_WA_X) ?
643 private->x - offset_x : CW_USEDEFAULT),
644 private->y - offset_y,
645 window_width, window_height,
650 if (GDK_WINDOW_HWND (window) != hwndNew)
652 g_warning ("gdk_window_new: gdk_event_translate::WM_CREATE (%p, %p) HWND mismatch.",
653 GDK_WINDOW_HWND (window),
656 /* HB: IHMO due to a race condition the handle was increased by
657 * one, which causes much trouble. Because I can't find the
658 * real bug, try to workaround it ...
659 * To reproduce: compile with MSVC 5, DEBUG=1
662 gdk_win32_handle_table_remove (GDK_WINDOW_HWND (window));
663 GDK_WINDOW_HWND (window) = hwndNew;
664 gdk_win32_handle_table_insert (&GDK_WINDOW_HWND (window), window);
666 /* the old behaviour, but with warning */
667 draw_impl->handle = hwndNew;
672 g_object_ref (window);
673 gdk_win32_handle_table_insert (&GDK_WINDOW_HWND (window), window);
675 GDK_NOTE (MISC, g_print ("... \"%s\" %dx%d@%+d%+d %p = %p\n",
677 window_width, window_height,
678 ((attributes_mask & GDK_WA_X) ?
679 private->x - offset_x: CW_USEDEFAULT),
680 private->y - offset_y,
682 GDK_WINDOW_HWND (window)));
684 /* Add window handle to title */
685 GDK_NOTE (MISC_OR_EVENTS, gdk_window_set_title (window, title));
689 if (draw_impl->handle == NULL)
691 WIN32_API_FAILED ("CreateWindowExW");
692 g_object_unref (window);
696 // if (!from_set_skip_taskbar_hint && private->window_type == GDK_WINDOW_TEMP)
697 // gdk_window_set_skip_taskbar_hint (window, TRUE);
699 gdk_window_set_cursor (window, ((attributes_mask & GDK_WA_CURSOR) ?
700 (attributes->cursor) :
705 gdk_window_foreign_new_for_display (GdkDisplay *display,
706 GdkNativeWindow anid)
709 GdkWindowObject *private;
710 GdkWindowImplWin32 *impl;
711 GdkDrawableImplWin32 *draw_impl;
717 g_return_val_if_fail (display == _gdk_display, NULL);
719 window = g_object_new (GDK_TYPE_WINDOW, NULL);
720 private = (GdkWindowObject *)window;
721 private->impl = g_object_new (_gdk_window_impl_get_type (), NULL);
722 impl = GDK_WINDOW_IMPL_WIN32 (private->impl);
723 draw_impl = GDK_DRAWABLE_IMPL_WIN32 (private->impl);
724 draw_impl->wrapper = GDK_DRAWABLE (window);
725 parent = GetParent ((HWND)anid);
727 private->parent = gdk_win32_handle_table_lookup ((GdkNativeWindow) parent);
728 if (!private->parent || GDK_WINDOW_TYPE (private->parent) == GDK_WINDOW_FOREIGN)
729 private->parent = (GdkWindowObject *)_gdk_root;
731 private->parent->children = g_list_prepend (private->parent->children, window);
733 draw_impl->handle = (HWND) anid;
734 GetClientRect ((HWND) anid, &rect);
736 point.y = rect.right;
737 ClientToScreen ((HWND) anid, &point);
738 if (parent != GetDesktopWindow ())
739 ScreenToClient (parent, &point);
740 private->x = point.x;
741 private->y = point.y;
742 private->width = rect.right - rect.left;
743 private->height = rect.bottom - rect.top;
744 private->window_type = GDK_WINDOW_FOREIGN;
745 private->destroyed = FALSE;
746 private->event_mask = GDK_ALL_EVENTS_MASK; /* XXX */
747 if (IsWindowVisible ((HWND) anid))
748 private->state &= (~GDK_WINDOW_STATE_WITHDRAWN);
750 private->state |= GDK_WINDOW_STATE_WITHDRAWN;
751 if (GetWindowLong ((HWND)anid, GWL_EXSTYLE) & WS_EX_TOPMOST)
752 private->state |= GDK_WINDOW_STATE_ABOVE;
754 private->state &= (~GDK_WINDOW_STATE_ABOVE);
755 private->state &= (~GDK_WINDOW_STATE_BELOW);
756 private->viewable = TRUE;
758 private->depth = gdk_visual_get_system ()->depth;
760 g_object_ref (window);
761 gdk_win32_handle_table_insert (&GDK_WINDOW_HWND (window), window);
763 GDK_NOTE (MISC, g_print ("gdk_window_foreign_new_for_display: %p: %s@%+d%+d\n",
765 _gdk_win32_drawable_description (window),
766 private->x, private->y));
772 gdk_window_lookup (GdkNativeWindow hwnd)
774 return (GdkWindow*) gdk_win32_handle_table_lookup (hwnd);
778 _gdk_win32_window_destroy (GdkWindow *window,
780 gboolean foreign_destroy)
782 GdkWindowObject *private = (GdkWindowObject *)window;
783 GdkWindowImplWin32 *window_impl = GDK_WINDOW_IMPL_WIN32 (private->impl);
786 g_return_if_fail (GDK_IS_WINDOW (window));
788 GDK_NOTE (MISC, g_print ("_gdk_win32_window_destroy: %p\n",
789 GDK_WINDOW_HWND (window)));
791 /* Remove ourself from the modal stack */
792 _gdk_remove_modal_window (window);
794 /* Remove all our transient children */
795 tmp = window_impl->transient_children;
798 GdkWindow *child = tmp->data;
799 GdkWindowImplWin32 *child_impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (child)->impl);
801 child_impl->transient_owner = NULL;
802 tmp = g_slist_next (tmp);
804 g_slist_free (window_impl->transient_children);
805 window_impl->transient_children = NULL;
807 /* Remove ourself from our transient owner */
808 if (window_impl->transient_owner != NULL)
810 gdk_window_set_transient_for (window, NULL);
813 if (!recursing && !foreign_destroy)
815 _gdk_win32_drawable_finish (private->impl);
817 private->destroyed = TRUE;
818 DestroyWindow (GDK_WINDOW_HWND (window));
821 gdk_win32_handle_table_remove (GDK_WINDOW_HWND (window));
825 _gdk_windowing_window_destroy_foreign (GdkWindow *window)
827 /* It's somebody else's window, but in our hierarchy, so reparent it
828 * to the desktop, and then try to destroy it.
830 gdk_window_hide (window);
831 gdk_window_reparent (window, NULL, 0, 0);
833 PostMessage (GDK_WINDOW_HWND (window), WM_CLOSE, 0, 0);
836 /* This function is called when the window really gone.
839 gdk_window_destroy_notify (GdkWindow *window)
841 g_return_if_fail (GDK_IS_WINDOW (window));
844 g_print ("gdk_window_destroy_notify: %p%s\n",
845 GDK_WINDOW_HWND (window),
846 (GDK_WINDOW_DESTROYED (window) ? " (destroyed)" : "")));
848 if (!GDK_WINDOW_DESTROYED (window))
850 if (GDK_WINDOW_TYPE (window) != GDK_WINDOW_FOREIGN)
851 g_warning ("window %p unexpectedly destroyed",
852 GDK_WINDOW_HWND (window));
854 _gdk_window_destroy (window, TRUE);
857 gdk_win32_handle_table_remove (GDK_WINDOW_HWND (window));
858 g_object_unref (window);
862 get_outer_rect (GdkWindow *window,
867 rect->left = rect->top = 0;
869 rect->bottom = height;
871 _gdk_win32_adjust_client_rect (window, rect);
875 adjust_for_gravity_hints (GdkWindow *window,
880 GdkWindowObject *obj;
881 GdkWindowImplWin32 *impl;
883 obj = GDK_WINDOW_OBJECT (window);
884 impl = GDK_WINDOW_IMPL_WIN32 (obj->impl);
886 if (impl->hint_flags & GDK_HINT_WIN_GRAVITY)
888 gint orig_x = *x, orig_y = *y;
890 switch (impl->hints.win_gravity)
892 case GDK_GRAVITY_NORTH:
893 case GDK_GRAVITY_CENTER:
894 case GDK_GRAVITY_SOUTH:
895 *x -= (outer_rect->right - outer_rect->left) / 2;
896 *x += obj->width / 2;
899 case GDK_GRAVITY_SOUTH_EAST:
900 case GDK_GRAVITY_EAST:
901 case GDK_GRAVITY_NORTH_EAST:
902 *x -= outer_rect->right - outer_rect->left;
906 case GDK_GRAVITY_STATIC:
907 *x += outer_rect->left;
914 switch (impl->hints.win_gravity)
916 case GDK_GRAVITY_WEST:
917 case GDK_GRAVITY_CENTER:
918 case GDK_GRAVITY_EAST:
919 *y -= (outer_rect->bottom - outer_rect->top) / 2;
920 *y += obj->height / 2;
923 case GDK_GRAVITY_SOUTH_WEST:
924 case GDK_GRAVITY_SOUTH:
925 case GDK_GRAVITY_SOUTH_EAST:
926 *y -= outer_rect->bottom - outer_rect->top;
930 case GDK_GRAVITY_STATIC:
931 *y += outer_rect->top;
938 (orig_x != *x || orig_y != *y) ?
939 g_print ("adjust_for_gravity_hints: x: %d->%d, y: %d->%d\n",
940 orig_x, *x, orig_y, *y)
946 show_window_internal (GdkWindow *window,
950 GdkWindowObject *private;
951 HWND old_active_window;
952 gboolean focus_on_map = TRUE;
956 private = (GdkWindowObject *) window;
958 if (private->destroyed)
961 GDK_NOTE (MISC, g_print ("show_window_internal: %p: %s%s%s\n",
962 GDK_WINDOW_HWND (window),
963 _gdk_win32_window_state_to_string (private->state),
964 (raise ? " raise" : ""),
965 (deiconify ? " deiconify" : "")));
967 /* If asked to show (not deiconify) an withdrawn and iconified
971 !GDK_WINDOW_IS_MAPPED (window) &&
972 (private->state & GDK_WINDOW_STATE_ICONIFIED))
974 ShowWindow (GDK_WINDOW_HWND (window), SW_MINIMIZE);
978 /* If asked to just show an iconified window, do nothing. */
979 if (!deiconify && (private->state & GDK_WINDOW_STATE_ICONIFIED))
982 /* If asked to deiconify an already noniconified window, do
983 * nothing. (Especially, don't cause the window to rise and
984 * activate. There are different calls for that.)
986 if (deiconify && !(private->state & GDK_WINDOW_STATE_ICONIFIED))
989 /* If asked to show (but not raise) a window that is already
990 * visible, do nothing.
992 if (!deiconify && !raise && IsWindowVisible (GDK_WINDOW_HWND (window)))
997 if (!GDK_WINDOW_IS_MAPPED (window))
999 gdk_synthesize_window_state (window,
1000 GDK_WINDOW_STATE_WITHDRAWN,
1002 focus_on_map = private->focus_on_map;
1005 exstyle = GetWindowLong (GDK_WINDOW_HWND (window), GWL_EXSTYLE);
1007 if (private->state & GDK_WINDOW_STATE_BELOW)
1008 exstyle &= (~WS_EX_TOPMOST);
1010 if (private->state & GDK_WINDOW_STATE_ABOVE)
1011 exstyle |= WS_EX_TOPMOST;
1013 if (exstyle & WS_EX_TOPMOST)
1018 /* Use SetWindowPos to show transparent windows so automatic redraws
1019 * in other windows can be suppressed.
1021 if (exstyle & WS_EX_TRANSPARENT)
1023 UINT flags = SWP_SHOWWINDOW | SWP_NOREDRAW | SWP_NOMOVE | SWP_NOSIZE;
1026 flags |= SWP_NOZORDER;
1027 if (!raise || GDK_WINDOW_TYPE (window) == GDK_WINDOW_TEMP || !focus_on_map)
1028 flags |= SWP_NOACTIVATE;
1030 SetWindowPos (GDK_WINDOW_HWND (window), top, 0, 0, 0, 0, flags);
1035 old_active_window = GetActiveWindow ();
1037 if (private->state & GDK_WINDOW_STATE_FULLSCREEN)
1039 gdk_window_fullscreen (window);
1041 else if (private->state & GDK_WINDOW_STATE_MAXIMIZED)
1043 ShowWindow (GDK_WINDOW_HWND (window), SW_MAXIMIZE);
1045 else if (private->state & GDK_WINDOW_STATE_ICONIFIED)
1047 ShowWindow (GDK_WINDOW_HWND (window), SW_RESTORE);
1049 else if (GDK_WINDOW_TYPE (window) == GDK_WINDOW_TEMP || !focus_on_map)
1051 ShowWindow (GDK_WINDOW_HWND (window), SW_SHOWNOACTIVATE);
1055 ShowWindow (GDK_WINDOW_HWND (window), SW_SHOWNORMAL);
1060 if (GDK_WINDOW_TYPE (window) == GDK_WINDOW_TEMP)
1061 SetWindowPos (GDK_WINDOW_HWND (window), HWND_TOPMOST,
1063 SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE);
1064 else if (GDK_WINDOW_TYPE (window) == GDK_WINDOW_TOPLEVEL ||
1065 GDK_WINDOW_TYPE (window) == GDK_WINDOW_DIALOG)
1067 if (focus_on_map && private->accept_focus)
1069 SetForegroundWindow (GDK_WINDOW_HWND (window));
1070 if (top == HWND_TOPMOST)
1071 SetWindowPos (GDK_WINDOW_HWND (window), top,
1073 SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE);
1077 SetWindowPos (GDK_WINDOW_HWND (window), top,
1079 SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE);
1084 BringWindowToTop (GDK_WINDOW_HWND (window));
1087 else if (old_active_window != GDK_WINDOW_HWND (window))
1089 SetActiveWindow (old_active_window);
1094 gdk_win32_window_show (GdkWindow *window,
1095 gboolean already_mapped)
1097 show_window_internal (window, FALSE, FALSE);
1101 gdk_win32_window_hide (GdkWindow *window)
1103 GdkWindowObject *private;
1105 private = (GdkWindowObject*) window;
1106 if (private->destroyed)
1109 GDK_NOTE (MISC, g_print ("gdk_win32_window_hide: %p: %s\n",
1110 GDK_WINDOW_HWND (window),
1111 _gdk_win32_window_state_to_string (private->state)));
1113 if (GDK_WINDOW_IS_MAPPED (window))
1114 gdk_synthesize_window_state (window,
1116 GDK_WINDOW_STATE_WITHDRAWN);
1118 _gdk_window_clear_update_area (window);
1120 if (GDK_WINDOW_TYPE (window) == GDK_WINDOW_TOPLEVEL)
1121 ShowOwnedPopups (GDK_WINDOW_HWND (window), FALSE);
1123 if (GetWindowLong (GDK_WINDOW_HWND (window), GWL_EXSTYLE) & WS_EX_TRANSPARENT)
1125 SetWindowPos (GDK_WINDOW_HWND (window), HWND_BOTTOM,
1127 SWP_HIDEWINDOW | SWP_NOREDRAW | SWP_NOZORDER | SWP_NOMOVE | SWP_NOSIZE);
1131 ShowWindow (GDK_WINDOW_HWND (window), SW_HIDE);
1136 gdk_win32_window_withdraw (GdkWindow *window)
1138 GdkWindowObject *private;
1140 private = (GdkWindowObject*) window;
1141 if (private->destroyed)
1144 GDK_NOTE (MISC, g_print ("gdk_win32_window_withdraw: %p: %s\n",
1145 GDK_WINDOW_HWND (window),
1146 _gdk_win32_window_state_to_string (private->state)));
1148 gdk_window_hide (window); /* ??? */
1152 gdk_win32_window_move (GdkWindow *window,
1155 GdkWindowObject *private = (GdkWindowObject *)window;
1156 GdkWindowImplWin32 *impl;
1158 g_return_if_fail (GDK_IS_WINDOW (window));
1160 if (GDK_WINDOW_DESTROYED (window))
1163 GDK_NOTE (MISC, g_print ("gdk_win32_window_move: %p: %+d%+d\n",
1164 GDK_WINDOW_HWND (window), x, y));
1166 impl = GDK_WINDOW_IMPL_WIN32 (private->impl);
1168 if (private->state & GDK_WINDOW_STATE_FULLSCREEN)
1171 /* Don't check GDK_WINDOW_TYPE (private) == GDK_WINDOW_CHILD.
1172 * Foreign windows (another app's windows) might be children of our
1173 * windows! Especially in the case of gtkplug/socket.
1175 if (GetAncestor (GDK_WINDOW_HWND (window), GA_PARENT) != GetDesktopWindow ())
1177 _gdk_window_move_resize_child (window, x, y, private->width, private->height);
1183 get_outer_rect (window, private->width, private->height, &outer_rect);
1185 adjust_for_gravity_hints (window, &outer_rect, &x, &y);
1187 GDK_NOTE (MISC, g_print ("... SetWindowPos(%p,NULL,%d,%d,0,0,"
1188 "NOACTIVATE|NOSIZE|NOZORDER)\n",
1189 GDK_WINDOW_HWND (window),
1190 x - _gdk_offset_x, y - _gdk_offset_y));
1192 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window), NULL,
1193 x - _gdk_offset_x, y - _gdk_offset_y, 0, 0,
1194 SWP_NOACTIVATE | SWP_NOSIZE | SWP_NOZORDER));
1199 gdk_win32_window_resize (GdkWindow *window,
1200 gint width, gint height)
1202 GdkWindowObject *private = (GdkWindowObject*) window;
1203 GdkWindowImplWin32 *impl;
1205 g_return_if_fail (GDK_IS_WINDOW (window));
1207 if (GDK_WINDOW_DESTROYED (window))
1215 GDK_NOTE (MISC, g_print ("gdk_win32_window_resize: %p: %dx%d\n",
1216 GDK_WINDOW_HWND (window), width, height));
1218 impl = GDK_WINDOW_IMPL_WIN32 (private->impl);
1220 if (private->state & GDK_WINDOW_STATE_FULLSCREEN)
1223 if (GetAncestor (GDK_WINDOW_HWND (window), GA_PARENT) != GetDesktopWindow ())
1225 _gdk_window_move_resize_child (window, private->x, private->y, width, height);
1231 get_outer_rect (window, width, height, &outer_rect);
1233 GDK_NOTE (MISC, g_print ("... SetWindowPos(%p,NULL,0,0,%ld,%ld,"
1234 "NOACTIVATE|NOMOVE|NOZORDER)\n",
1235 GDK_WINDOW_HWND (window),
1236 outer_rect.right - outer_rect.left,
1237 outer_rect.bottom - outer_rect.top));
1239 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window), NULL,
1241 outer_rect.right - outer_rect.left,
1242 outer_rect.bottom - outer_rect.top,
1243 SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOZORDER));
1244 private->resize_count += 1;
1249 gdk_win32_window_move_resize_internal (GdkWindow *window,
1255 GdkWindowObject *private;
1256 GdkWindowImplWin32 *impl;
1258 g_return_if_fail (GDK_IS_WINDOW (window));
1260 if (GDK_WINDOW_DESTROYED (window))
1268 private = GDK_WINDOW_OBJECT (window);
1269 impl = GDK_WINDOW_IMPL_WIN32 (private->impl);
1271 if (private->state & GDK_WINDOW_STATE_FULLSCREEN)
1274 GDK_NOTE (MISC, g_print ("gdk_win32_window_move_resize: %p: %dx%d@%+d%+d\n",
1275 GDK_WINDOW_HWND (window),
1276 width, height, x, y));
1278 if (GetAncestor (GDK_WINDOW_HWND (window), GA_PARENT) != GetDesktopWindow ())
1280 _gdk_window_move_resize_child (window, x, y, width, height);
1286 get_outer_rect (window, width, height, &outer_rect);
1288 adjust_for_gravity_hints (window, &outer_rect, &x, &y);
1290 GDK_NOTE (MISC, g_print ("... SetWindowPos(%p,NULL,%d,%d,%ld,%ld,"
1291 "NOACTIVATE|NOZORDER)\n",
1292 GDK_WINDOW_HWND (window),
1293 x - _gdk_offset_x, y - _gdk_offset_y,
1294 outer_rect.right - outer_rect.left,
1295 outer_rect.bottom - outer_rect.top));
1297 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window), NULL,
1298 x - _gdk_offset_x, y - _gdk_offset_y,
1299 outer_rect.right - outer_rect.left,
1300 outer_rect.bottom - outer_rect.top,
1301 SWP_NOACTIVATE | SWP_NOZORDER));
1306 gdk_win32_window_move_resize (GdkWindow *window,
1313 if (with_move && (width < 0 && height < 0))
1315 gdk_win32_window_move (window, x, y);
1321 gdk_win32_window_move_resize_internal (window, x, y, width, height);
1325 gdk_win32_window_resize (window, width, height);
1331 gdk_win32_window_reparent (GdkWindow *window,
1332 GdkWindow *new_parent,
1336 GdkWindowObject *window_private;
1337 GdkWindowObject *parent_private;
1338 GdkWindowObject *old_parent_private;
1339 GdkWindowImplWin32 *impl;
1340 gboolean was_toplevel;
1344 new_parent = _gdk_root;
1346 window_private = (GdkWindowObject*) window;
1347 old_parent_private = (GdkWindowObject *) window_private->parent;
1348 parent_private = (GdkWindowObject*) new_parent;
1349 impl = GDK_WINDOW_IMPL_WIN32 (window_private->impl);
1351 GDK_NOTE (MISC, g_print ("gdk_win32_window_reparent: %p: %p\n",
1352 GDK_WINDOW_HWND (window),
1353 GDK_WINDOW_HWND (new_parent)));
1355 style = GetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE);
1357 was_toplevel = GetAncestor (GDK_WINDOW_HWND (window), GA_PARENT) == GetDesktopWindow ();
1358 if (was_toplevel && new_parent != _gdk_root)
1360 /* Reparenting from top-level (child of desktop). Clear out
1363 style &= ~(WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME | WS_MINIMIZEBOX | WS_MAXIMIZEBOX);
1365 SetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE, style);
1367 else if (new_parent == _gdk_root)
1369 /* Reparenting to top-level. Add decorations. */
1370 style &= ~(WS_CHILD);
1371 style |= WS_OVERLAPPEDWINDOW;
1372 SetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE, style);
1375 API_CALL (SetParent, (GDK_WINDOW_HWND (window),
1376 GDK_WINDOW_HWND (new_parent)));
1378 API_CALL (MoveWindow, (GDK_WINDOW_HWND (window),
1379 x, y, window_private->width, window_private->height, TRUE));
1381 /* From here on, we treat parents of type GDK_WINDOW_FOREIGN like
1384 if (GDK_WINDOW_TYPE (new_parent) == GDK_WINDOW_FOREIGN)
1385 new_parent = _gdk_root;
1387 window_private->parent = (GdkWindowObject *)new_parent;
1389 /* Switch the window type as appropriate */
1391 switch (GDK_WINDOW_TYPE (new_parent))
1393 case GDK_WINDOW_ROOT:
1394 if (impl->toplevel_window_type != -1)
1395 GDK_WINDOW_TYPE (window) = impl->toplevel_window_type;
1396 else if (GDK_WINDOW_TYPE (window) == GDK_WINDOW_CHILD)
1397 GDK_WINDOW_TYPE (window) = GDK_WINDOW_TOPLEVEL;
1400 case GDK_WINDOW_TOPLEVEL:
1401 case GDK_WINDOW_CHILD:
1402 case GDK_WINDOW_DIALOG:
1403 case GDK_WINDOW_TEMP:
1404 if (WINDOW_IS_TOPLEVEL (window))
1406 /* Save the original window type so we can restore it if the
1407 * window is reparented back to be a toplevel.
1409 impl->toplevel_window_type = GDK_WINDOW_TYPE (window);
1410 GDK_WINDOW_TYPE (window) = GDK_WINDOW_CHILD;
1414 if (old_parent_private)
1415 old_parent_private->children =
1416 g_list_remove (old_parent_private->children, window);
1418 parent_private->children = g_list_prepend (parent_private->children, window);
1424 gdk_win32_window_raise (GdkWindow *window)
1426 if (!GDK_WINDOW_DESTROYED (window))
1428 GDK_NOTE (MISC, g_print ("gdk_win32_window_raise: %p\n",
1429 GDK_WINDOW_HWND (window)));
1431 if (GDK_WINDOW_TYPE (window) == GDK_WINDOW_TEMP)
1432 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window), HWND_TOPMOST,
1434 SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE));
1435 else if (((GdkWindowObject *)window)->accept_focus)
1436 API_CALL (BringWindowToTop, (GDK_WINDOW_HWND (window)));
1438 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window), HWND_TOP,
1440 SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE));
1445 gdk_win32_window_lower (GdkWindow *window)
1447 if (!GDK_WINDOW_DESTROYED (window))
1449 GDK_NOTE (MISC, g_print ("gdk_win32_window_lower: %p\n"
1450 "... SetWindowPos(%p,HWND_BOTTOM,0,0,0,0,"
1451 "NOACTIVATE|NOMOVE|NOSIZE)\n",
1452 GDK_WINDOW_HWND (window),
1453 GDK_WINDOW_HWND (window)));
1455 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window), HWND_BOTTOM,
1457 SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE));
1462 gdk_window_set_urgency_hint (GdkWindow *window,
1465 FLASHWINFO flashwinfo;
1466 typedef BOOL (*PFN_FlashWindowEx) (FLASHWINFO*);
1467 PFN_FlashWindowEx flashWindowEx = NULL;
1469 g_return_if_fail (GDK_IS_WINDOW (window));
1470 g_return_if_fail (GDK_WINDOW_TYPE (window) != GDK_WINDOW_CHILD);
1472 if (GDK_WINDOW_DESTROYED (window))
1475 flashWindowEx = (PFN_FlashWindowEx) GetProcAddress (GetModuleHandle ("user32.dll"), "FlashWindowEx");
1479 flashwinfo.cbSize = sizeof (flashwinfo);
1480 flashwinfo.hwnd = GDK_WINDOW_HWND (window);
1482 flashwinfo.dwFlags = FLASHW_ALL | FLASHW_TIMER;
1484 flashwinfo.dwFlags = FLASHW_STOP;
1485 flashwinfo.uCount = 0;
1486 flashwinfo.dwTimeout = 0;
1488 flashWindowEx (&flashwinfo);
1492 FlashWindow (GDK_WINDOW_HWND (window), urgent);
1497 get_effective_window_decorations (GdkWindow *window,
1498 GdkWMDecoration *decoration)
1500 GdkWindowImplWin32 *impl;
1502 impl = (GdkWindowImplWin32 *)((GdkWindowObject *)window)->impl;
1504 if (gdk_window_get_decorations (window, decoration))
1507 if (((GdkWindowObject *) window)->window_type != GDK_WINDOW_TOPLEVEL &&
1508 ((GdkWindowObject *) window)->window_type != GDK_WINDOW_DIALOG)
1513 if ((impl->hint_flags & GDK_HINT_MIN_SIZE) &&
1514 (impl->hint_flags & GDK_HINT_MAX_SIZE) &&
1515 impl->hints.min_width == impl->hints.max_width &&
1516 impl->hints.min_height == impl->hints.max_height)
1518 *decoration = GDK_DECOR_ALL | GDK_DECOR_RESIZEH | GDK_DECOR_MAXIMIZE;
1520 if (impl->type_hint == GDK_WINDOW_TYPE_HINT_DIALOG ||
1521 impl->type_hint == GDK_WINDOW_TYPE_HINT_MENU ||
1522 impl->type_hint == GDK_WINDOW_TYPE_HINT_TOOLBAR)
1524 *decoration |= GDK_DECOR_MINIMIZE;
1526 else if (impl->type_hint == GDK_WINDOW_TYPE_HINT_SPLASHSCREEN)
1528 *decoration |= GDK_DECOR_MENU | GDK_DECOR_MINIMIZE;
1533 else if (impl->hint_flags & GDK_HINT_MAX_SIZE)
1535 *decoration = GDK_DECOR_ALL | GDK_DECOR_MAXIMIZE;
1536 if (impl->type_hint == GDK_WINDOW_TYPE_HINT_DIALOG ||
1537 impl->type_hint == GDK_WINDOW_TYPE_HINT_MENU ||
1538 impl->type_hint == GDK_WINDOW_TYPE_HINT_TOOLBAR)
1540 *decoration |= GDK_DECOR_MINIMIZE;
1547 switch (impl->type_hint)
1549 case GDK_WINDOW_TYPE_HINT_DIALOG:
1550 *decoration = (GDK_DECOR_ALL | GDK_DECOR_MINIMIZE | GDK_DECOR_MAXIMIZE);
1553 case GDK_WINDOW_TYPE_HINT_MENU:
1554 *decoration = (GDK_DECOR_ALL | GDK_DECOR_RESIZEH | GDK_DECOR_MINIMIZE | GDK_DECOR_MAXIMIZE);
1557 case GDK_WINDOW_TYPE_HINT_TOOLBAR:
1558 case GDK_WINDOW_TYPE_HINT_UTILITY:
1559 gdk_window_set_skip_taskbar_hint (window, TRUE);
1560 gdk_window_set_skip_pager_hint (window, TRUE);
1561 *decoration = (GDK_DECOR_ALL | GDK_DECOR_MINIMIZE | GDK_DECOR_MAXIMIZE);
1564 case GDK_WINDOW_TYPE_HINT_SPLASHSCREEN:
1565 *decoration = (GDK_DECOR_ALL | GDK_DECOR_RESIZEH | GDK_DECOR_MENU |
1566 GDK_DECOR_MINIMIZE | GDK_DECOR_MAXIMIZE);
1569 case GDK_WINDOW_TYPE_HINT_DOCK:
1572 case GDK_WINDOW_TYPE_HINT_DESKTOP:
1577 case GDK_WINDOW_TYPE_HINT_NORMAL:
1578 *decoration = GDK_DECOR_ALL;
1587 gdk_window_set_geometry_hints (GdkWindow *window,
1588 const GdkGeometry *geometry,
1589 GdkWindowHints geom_mask)
1591 GdkWindowImplWin32 *impl;
1593 g_return_if_fail (GDK_IS_WINDOW (window));
1595 if (GDK_WINDOW_DESTROYED (window))
1598 GDK_NOTE (MISC, g_print ("gdk_window_set_geometry_hints: %p\n",
1599 GDK_WINDOW_HWND (window)));
1601 impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (window)->impl);
1603 impl->hint_flags = geom_mask;
1604 impl->hints = *geometry;
1606 if (geom_mask & GDK_HINT_POS)
1607 ; /* even the X11 mplementation doesn't care */
1609 if (geom_mask & GDK_HINT_MIN_SIZE)
1611 GDK_NOTE (MISC, g_print ("... MIN_SIZE: %dx%d\n",
1612 geometry->min_width, geometry->min_height));
1615 if (geom_mask & GDK_HINT_MAX_SIZE)
1617 GDK_NOTE (MISC, g_print ("... MAX_SIZE: %dx%d\n",
1618 geometry->max_width, geometry->max_height));
1621 if (geom_mask & GDK_HINT_BASE_SIZE)
1623 GDK_NOTE (MISC, g_print ("... BASE_SIZE: %dx%d\n",
1624 geometry->base_width, geometry->base_height));
1627 if (geom_mask & GDK_HINT_RESIZE_INC)
1629 GDK_NOTE (MISC, g_print ("... RESIZE_INC: (%d,%d)\n",
1630 geometry->width_inc, geometry->height_inc));
1633 if (geom_mask & GDK_HINT_ASPECT)
1635 GDK_NOTE (MISC, g_print ("... ASPECT: %g--%g\n",
1636 geometry->min_aspect, geometry->max_aspect));
1639 if (geom_mask & GDK_HINT_WIN_GRAVITY)
1641 GDK_NOTE (MISC, g_print ("... GRAVITY: %d\n", geometry->win_gravity));
1644 update_style_bits (window);
1648 gdk_window_set_title (GdkWindow *window,
1653 g_return_if_fail (GDK_IS_WINDOW (window));
1654 g_return_if_fail (title != NULL);
1656 if (GDK_WINDOW_DESTROYED (window))
1659 /* Empty window titles not allowed, so set it to just a period. */
1663 GDK_NOTE (MISC, g_print ("gdk_window_set_title: %p: %s\n",
1664 GDK_WINDOW_HWND (window), title));
1666 GDK_NOTE (MISC_OR_EVENTS, title = g_strdup_printf ("%p %s", GDK_WINDOW_HWND (window), title));
1668 wtitle = g_utf8_to_utf16 (title, -1, NULL, NULL, NULL);
1669 API_CALL (SetWindowTextW, (GDK_WINDOW_HWND (window), wtitle));
1672 GDK_NOTE (MISC_OR_EVENTS, g_free ((char *) title));
1676 gdk_window_set_role (GdkWindow *window,
1679 g_return_if_fail (GDK_IS_WINDOW (window));
1681 GDK_NOTE (MISC, g_print ("gdk_window_set_role: %p: %s\n",
1682 GDK_WINDOW_HWND (window),
1683 (role ? role : "NULL")));
1688 gdk_window_set_transient_for (GdkWindow *window,
1691 HWND window_id, parent_id;
1692 GdkWindowImplWin32 *window_impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (window)->impl);
1693 GdkWindowImplWin32 *parent_impl = NULL;
1696 g_return_if_fail (GDK_IS_WINDOW (window));
1698 window_id = GDK_WINDOW_HWND (window);
1699 parent_id = parent != NULL ? GDK_WINDOW_HWND (parent) : NULL;
1701 GDK_NOTE (MISC, g_print ("gdk_window_set_transient_for: %p: %p\n", window_id, parent_id));
1703 if (GDK_WINDOW_DESTROYED (window) || (parent && GDK_WINDOW_DESTROYED (parent)))
1705 if (GDK_WINDOW_DESTROYED (window))
1706 GDK_NOTE (MISC, g_print ("... destroyed!\n"));
1708 GDK_NOTE (MISC, g_print ("... owner destroyed!\n"));
1713 if (((GdkWindowObject *) window)->window_type == GDK_WINDOW_CHILD)
1715 GDK_NOTE (MISC, g_print ("... a child window!\n"));
1721 GdkWindowImplWin32 *trans_impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (window_impl->transient_owner)->impl);
1722 if (trans_impl->transient_children != NULL)
1724 item = g_slist_find (trans_impl->transient_children, window);
1726 trans_impl->transient_children = g_slist_delete_link (trans_impl->transient_children, item);
1727 trans_impl->num_transients--;
1729 if (!trans_impl->num_transients)
1731 trans_impl->transient_children = NULL;
1734 g_object_unref (G_OBJECT (window_impl->transient_owner));
1735 g_object_unref (G_OBJECT (window));
1737 window_impl->transient_owner = NULL;
1741 parent_impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (parent)->impl);
1743 parent_impl->transient_children = g_slist_append (parent_impl->transient_children, window);
1744 g_object_ref (G_OBJECT (window));
1745 parent_impl->num_transients++;
1746 window_impl->transient_owner = parent;
1747 g_object_ref (G_OBJECT (parent));
1750 /* This changes the *owner* of the window, despite the misleading
1751 * name. (Owner and parent are unrelated concepts.) At least that's
1752 * what people who seem to know what they talk about say on
1753 * USENET. Search on Google.
1756 if (SetWindowLongPtr (window_id, GWLP_HWNDPARENT, (LONG_PTR) parent_id) == 0 &&
1757 GetLastError () != 0)
1758 WIN32_API_FAILED ("SetWindowLongPtr");
1762 _gdk_push_modal_window (GdkWindow *window)
1764 modal_window_stack = g_slist_prepend (modal_window_stack,
1769 _gdk_remove_modal_window (GdkWindow *window)
1773 g_return_if_fail (window != NULL);
1775 /* It's possible to be NULL here if someone sets the modal hint of the window
1776 * to FALSE before a modal window stack has ever been created. */
1777 if (modal_window_stack == NULL)
1780 /* Find the requested window in the stack and remove it. Yeah, I realize this
1781 * means we're not a 'real stack', strictly speaking. Sue me. :) */
1782 tmp = g_slist_find (modal_window_stack, window);
1785 modal_window_stack = g_slist_delete_link (modal_window_stack, tmp);
1790 _gdk_modal_current (void)
1792 if (modal_window_stack != NULL)
1794 GSList *tmp = modal_window_stack;
1796 while (tmp != NULL && !GDK_WINDOW_IS_MAPPED (tmp->data))
1798 tmp = g_slist_next (tmp);
1801 return tmp != NULL ? tmp->data : NULL;
1810 gdk_win32_window_set_background (GdkWindow *window,
1811 const GdkColor *color)
1813 GdkWindowObject *private = (GdkWindowObject *)window;
1815 GDK_NOTE (MISC, g_print ("gdk_win32_window_set_background: %p: %s\n",
1816 GDK_WINDOW_HWND (window),
1817 _gdk_win32_color_to_string (color)));
1819 private->bg_color = *color;
1823 gdk_win32_window_set_back_pixmap (GdkWindow *window,
1826 /* TODO_CSW? but win32 has no XSetWindowBackgroundPixmap */
1830 gdk_win32_window_set_device_cursor (GdkWindow *window,
1834 GdkWindowImplWin32 *impl;
1835 GdkCursorPrivate *cursor_private;
1837 HCURSOR hprevcursor;
1839 impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (window)->impl);
1840 cursor_private = (GdkCursorPrivate*) cursor;
1842 if (GDK_WINDOW_DESTROYED (window))
1848 hcursor = cursor_private->hcursor;
1850 GDK_NOTE (MISC, g_print ("gdk_win32_window_set_cursor: %p: %p\n",
1851 GDK_WINDOW_HWND (window),
1854 /* First get the old cursor, if any (we wait to free the old one
1855 * since it may be the current cursor set in the Win32 API right
1858 hprevcursor = impl->hcursor;
1860 GDK_DEVICE_GET_CLASS (device)->set_window_cursor (device, window, cursor);
1862 if (hcursor == NULL)
1863 impl->hcursor = NULL;
1866 /* We must copy the cursor as it is OK to destroy the GdkCursor
1867 * while still in use for some window. See for instance
1868 * gimp_change_win_cursor() which calls gdk_window_set_cursor
1869 * (win, cursor), and immediately afterwards gdk_cursor_destroy
1872 if ((impl->hcursor = CopyCursor (hcursor)) == NULL)
1873 WIN32_API_FAILED ("CopyCursor");
1874 GDK_NOTE (MISC, g_print ("... CopyCursor (%p) = %p\n",
1875 hcursor, impl->hcursor));
1878 /* Destroy the previous cursor */
1879 if (hprevcursor != NULL)
1881 GDK_NOTE (MISC, g_print ("... DestroyCursor (%p)\n", hprevcursor));
1882 API_CALL (DestroyCursor, (hprevcursor));
1887 gdk_win32_window_get_geometry (GdkWindow *window,
1897 if (!GDK_WINDOW_DESTROYED (window))
1901 API_CALL (GetClientRect, (GDK_WINDOW_HWND (window), &rect));
1903 if (window != _gdk_root)
1906 GdkWindow *parent = gdk_window_get_parent (window);
1910 ClientToScreen (GDK_WINDOW_HWND (window), &pt);
1911 ScreenToClient (GDK_WINDOW_HWND (parent), &pt);
1917 ClientToScreen (GDK_WINDOW_HWND (window), &pt);
1918 ScreenToClient (GDK_WINDOW_HWND (parent), &pt);
1922 if (parent == _gdk_root)
1924 rect.left += _gdk_offset_x;
1925 rect.top += _gdk_offset_y;
1926 rect.right += _gdk_offset_x;
1927 rect.bottom += _gdk_offset_y;
1936 *width = rect.right - rect.left;
1938 *height = rect.bottom - rect.top;
1940 *depth = gdk_drawable_get_visual (window)->depth;
1942 GDK_NOTE (MISC, g_print ("gdk_win32_window_get_geometry: %p: %ldx%ldx%d@%+ld%+ld\n",
1943 GDK_WINDOW_HWND (window),
1944 rect.right - rect.left, rect.bottom - rect.top,
1945 gdk_drawable_get_visual (window)->depth,
1946 rect.left, rect.top));
1951 gdk_win32_window_get_root_coords (GdkWindow *window,
1963 ClientToScreen (GDK_WINDOW_HWND (window), &pt);
1968 *root_x = tx + _gdk_offset_x;
1970 *root_y = ty + _gdk_offset_y;
1972 GDK_NOTE (MISC, g_print ("gdk_win32_window_get_root_coords: %p: %+d%+d %+d%+d\n",
1973 GDK_WINDOW_HWND (window),
1975 tx + _gdk_offset_x, ty + _gdk_offset_y));
1980 gdk_win32_window_get_deskrelative_origin (GdkWindow *window,
1984 return gdk_win32_window_get_root_coords (window, 0, 0, x, y);
1988 gdk_win32_window_restack_under (GdkWindow *window,
1989 GList *native_siblings)
1995 gdk_win32_window_restack_toplevel (GdkWindow *window,
2003 gdk_window_get_root_origin (GdkWindow *window,
2009 g_return_if_fail (GDK_IS_WINDOW (window));
2011 gdk_window_get_frame_extents (window, &rect);
2019 GDK_NOTE (MISC, g_print ("gdk_window_get_root_origin: %p: %+d%+d\n",
2020 GDK_WINDOW_HWND (window), rect.x, rect.y));
2024 gdk_window_get_frame_extents (GdkWindow *window,
2027 GdkWindowObject *private;
2031 g_return_if_fail (GDK_IS_WINDOW (window));
2032 g_return_if_fail (rect != NULL);
2034 private = GDK_WINDOW_OBJECT (window);
2041 if (GDK_WINDOW_DESTROYED (window))
2044 /* FIXME: window is documented to be a toplevel GdkWindow, so is it really
2045 * necessary to walk its parent chain?
2047 while (private->parent && ((GdkWindowObject*) private->parent)->parent)
2048 private = (GdkWindowObject*) private->parent;
2050 hwnd = GDK_WINDOW_HWND (window);
2051 API_CALL (GetWindowRect, (hwnd, &r));
2053 rect->x = r.left + _gdk_offset_x;
2054 rect->y = r.top + _gdk_offset_y;
2055 rect->width = r.right - r.left;
2056 rect->height = r.bottom - r.top;
2058 GDK_NOTE (MISC, g_print ("gdk_window_get_frame_extents: %p: %ldx%ld@%+ld%+ld\n",
2059 GDK_WINDOW_HWND (window),
2060 r.right - r.left, r.bottom - r.top,
2065 gdk_window_win32_get_device_state (GdkWindow *window,
2069 GdkModifierType *mask)
2073 g_return_val_if_fail (window == NULL || GDK_IS_WINDOW (window), FALSE);
2075 GDK_DEVICE_GET_CLASS (device)->query_state (device, window,
2079 return (child != NULL);
2083 _gdk_windowing_get_device_state (GdkDisplay *display,
2088 GdkModifierType *mask)
2090 g_return_if_fail (display == _gdk_display);
2093 *screen = _gdk_screen;
2095 GDK_DEVICE_GET_CLASS (device)->query_state (device,
2096 gdk_screen_get_root_window (_gdk_screen),
2104 gdk_display_warp_pointer (GdkDisplay *display,
2109 GdkDeviceManagerWin32 *device_manager;
2111 g_return_if_fail (display == _gdk_display);
2112 g_return_if_fail (screen == _gdk_screen);
2114 device_manager = GDK_DEVICE_MANAGER_WIN32 (gdk_display_get_device_manager (display));
2115 GDK_DEVICE_GET_CLASS (device_manager->core_pointer)->warp (device_manager->core_pointer,
2120 gdk_display_warp_device (GdkDisplay *display,
2126 g_return_if_fail (display == _gdk_display);
2127 g_return_if_fail (screen == _gdk_screen);
2128 g_return_if_fail (GDK_IS_DEVICE (device));
2129 g_return_if_fail (display == gdk_device_get_display (device));
2131 GDK_DEVICE_GET_CLASS (device)->warp (device, screen, x, y);
2135 _gdk_windowing_window_at_device_position (GdkDisplay *display,
2139 GdkModifierType *mask,
2140 gboolean get_toplevel)
2142 return GDK_DEVICE_GET_CLASS (device)->window_at_position (device, win_x, win_y, mask, get_toplevel);
2146 gdk_win32_window_get_events (GdkWindow *window)
2148 if (GDK_WINDOW_DESTROYED (window))
2151 return GDK_WINDOW_OBJECT (window)->event_mask;
2155 gdk_win32_window_set_events (GdkWindow *window,
2156 GdkEventMask event_mask)
2158 /* gdk_window_new() always sets the GDK_STRUCTURE_MASK, so better
2159 * set it here, too. Not that I know or remember why it is
2160 * necessary, will have to test some day.
2162 GDK_WINDOW_OBJECT (window)->event_mask = GDK_STRUCTURE_MASK | event_mask;
2166 do_shape_combine_region (GdkWindow *window,
2172 GetClientRect (GDK_WINDOW_HWND (window), &rect);
2173 _gdk_win32_adjust_client_rect (window, &rect);
2175 OffsetRgn (hrgn, -rect.left, -rect.top);
2176 OffsetRgn (hrgn, x, y);
2178 /* If this is a top-level window, add the title bar to the region */
2179 if (GDK_WINDOW_TYPE (window) == GDK_WINDOW_TOPLEVEL)
2181 HRGN tmp = CreateRectRgn (0, 0, rect.right - rect.left, -rect.top);
2182 CombineRgn (hrgn, hrgn, tmp, RGN_OR);
2186 SetWindowRgn (GDK_WINDOW_HWND (window), hrgn, TRUE);
2190 gdk_window_set_override_redirect (GdkWindow *window,
2191 gboolean override_redirect)
2193 g_return_if_fail (GDK_IS_WINDOW (window));
2195 g_warning ("gdk_window_set_override_redirect not implemented");
2199 gdk_window_set_accept_focus (GdkWindow *window,
2200 gboolean accept_focus)
2202 GdkWindowObject *private;
2204 g_return_if_fail (GDK_IS_WINDOW (window));
2206 private = (GdkWindowObject *)window;
2208 accept_focus = accept_focus != FALSE;
2210 if (private->accept_focus != accept_focus)
2211 private->accept_focus = accept_focus;
2215 gdk_window_set_focus_on_map (GdkWindow *window,
2216 gboolean focus_on_map)
2218 GdkWindowObject *private;
2220 g_return_if_fail (GDK_IS_WINDOW (window));
2222 private = (GdkWindowObject *)window;
2224 focus_on_map = focus_on_map != FALSE;
2226 if (private->focus_on_map != focus_on_map)
2227 private->focus_on_map = focus_on_map;
2231 gdk_window_set_icon_list (GdkWindow *window,
2234 GdkPixbuf *pixbuf, *big_pixbuf, *small_pixbuf;
2235 gint big_diff, small_diff;
2236 gint big_w, big_h, small_w, small_h;
2239 HICON small_hicon, big_hicon;
2240 GdkWindowImplWin32 *impl;
2241 gint i, big_i, small_i;
2243 g_return_if_fail (GDK_IS_WINDOW (window));
2245 if (GDK_WINDOW_DESTROYED (window))
2248 impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (window)->impl);
2250 /* ideal sizes for small and large icons */
2251 big_w = GetSystemMetrics (SM_CXICON);
2252 big_h = GetSystemMetrics (SM_CYICON);
2253 small_w = GetSystemMetrics (SM_CXSMICON);
2254 small_h = GetSystemMetrics (SM_CYSMICON);
2256 /* find closest sized icons in the list */
2258 small_pixbuf = NULL;
2264 pixbuf = (GdkPixbuf*) pixbufs->data;
2265 w = gdk_pixbuf_get_width (pixbuf);
2266 h = gdk_pixbuf_get_height (pixbuf);
2268 dw = ABS (w - big_w);
2269 dh = ABS (h - big_h);
2270 diff = dw*dw + dh*dh;
2271 if (big_pixbuf == NULL || diff < big_diff)
2273 big_pixbuf = pixbuf;
2278 dw = ABS (w - small_w);
2279 dh = ABS (h - small_h);
2280 diff = dw*dw + dh*dh;
2281 if (small_pixbuf == NULL || diff < small_diff)
2283 small_pixbuf = pixbuf;
2288 pixbufs = g_list_next (pixbufs);
2292 /* Create the icons */
2293 big_hicon = _gdk_win32_pixbuf_to_hicon (big_pixbuf);
2294 small_hicon = _gdk_win32_pixbuf_to_hicon (small_pixbuf);
2297 SendMessageW (GDK_WINDOW_HWND (window), WM_SETICON, ICON_BIG,
2299 SendMessageW (GDK_WINDOW_HWND (window), WM_SETICON, ICON_SMALL,
2300 (LPARAM)small_hicon);
2302 /* Store the icons, destroying any previous icons */
2303 if (impl->hicon_big)
2304 GDI_CALL (DestroyIcon, (impl->hicon_big));
2305 impl->hicon_big = big_hicon;
2306 if (impl->hicon_small)
2307 GDI_CALL (DestroyIcon, (impl->hicon_small));
2308 impl->hicon_small = small_hicon;
2312 gdk_window_set_icon (GdkWindow *window,
2313 GdkWindow *icon_window,
2317 g_return_if_fail (GDK_IS_WINDOW (window));
2319 /* do nothing, use gdk_window_set_icon_list instead */
2323 gdk_window_set_icon_name (GdkWindow *window,
2326 /* In case I manage to confuse this again (or somebody else does):
2327 * Please note that "icon name" here really *does* mean the name or
2328 * title of an window minimized as an icon on the desktop, or in the
2329 * taskbar. It has nothing to do with the freedesktop.org icon
2333 g_return_if_fail (GDK_IS_WINDOW (window));
2335 if (GDK_WINDOW_DESTROYED (window))
2339 /* This is not the correct thing to do. We should keep both the
2340 * "normal" window title, and the icon name. When the window is
2341 * minimized, call SetWindowText() with the icon name, and when the
2342 * window is restored, with the normal window title. Also, the name
2343 * is in UTF-8, so we should do the normal conversion to either wide
2344 * chars or system codepage, and use either the W or A version of
2345 * SetWindowText(), depending on Windows version.
2347 API_CALL (SetWindowText, (GDK_WINDOW_HWND (window), name));
2352 gdk_window_get_group (GdkWindow *window)
2354 g_return_val_if_fail (GDK_IS_WINDOW (window), NULL);
2355 g_return_val_if_fail (GDK_WINDOW_TYPE (window) != GDK_WINDOW_CHILD, NULL);
2357 if (GDK_WINDOW_DESTROYED (window))
2360 g_warning ("gdk_window_get_group not yet implemented");
2366 gdk_window_set_group (GdkWindow *window,
2369 g_return_if_fail (GDK_IS_WINDOW (window));
2370 g_return_if_fail (GDK_WINDOW_TYPE (window) != GDK_WINDOW_CHILD);
2371 g_return_if_fail (leader == NULL || GDK_IS_WINDOW (leader));
2373 if (GDK_WINDOW_DESTROYED (window) || GDK_WINDOW_DESTROYED (leader))
2376 g_warning ("gdk_window_set_group not implemented");
2380 update_single_bit (LONG *style,
2385 /* all controls the interpretation of gdk_bit -- if all is TRUE,
2386 * gdk_bit indicates whether style_bit is off; if all is FALSE, gdk
2387 * bit indicate whether style_bit is on
2389 if ((!all && gdk_bit) || (all && !gdk_bit))
2390 *style |= style_bit;
2392 *style &= ~style_bit;
2396 update_style_bits (GdkWindow *window)
2398 GdkWindowObject *private = (GdkWindowObject *)window;
2399 GdkWindowImplWin32 *impl = (GdkWindowImplWin32 *)private->impl;
2400 GdkWMDecoration decorations;
2401 LONG old_style, new_style, old_exstyle, new_exstyle;
2403 RECT rect, before, after;
2405 old_style = GetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE);
2406 old_exstyle = GetWindowLong (GDK_WINDOW_HWND (window), GWL_EXSTYLE);
2408 GetClientRect (GDK_WINDOW_HWND (window), &before);
2410 AdjustWindowRectEx (&before, old_style, FALSE, old_exstyle);
2412 new_style = old_style;
2413 new_exstyle = old_exstyle;
2415 if (private->window_type == GDK_WINDOW_TEMP ||
2416 impl->type_hint == GDK_WINDOW_TYPE_HINT_UTILITY)
2417 new_exstyle |= WS_EX_TOOLWINDOW;
2419 new_exstyle &= ~WS_EX_TOOLWINDOW;
2421 if (get_effective_window_decorations (window, &decorations))
2423 all = (decorations & GDK_DECOR_ALL);
2424 update_single_bit (&new_style, all, decorations & GDK_DECOR_BORDER, WS_BORDER);
2425 update_single_bit (&new_style, all, decorations & GDK_DECOR_RESIZEH, WS_THICKFRAME);
2426 update_single_bit (&new_style, all, decorations & GDK_DECOR_TITLE, WS_CAPTION);
2427 update_single_bit (&new_style, all, decorations & GDK_DECOR_MENU, WS_SYSMENU);
2428 update_single_bit (&new_style, all, decorations & GDK_DECOR_MINIMIZE, WS_MINIMIZEBOX);
2429 update_single_bit (&new_style, all, decorations & GDK_DECOR_MAXIMIZE, WS_MAXIMIZEBOX);
2432 if (old_style == new_style && old_exstyle == new_exstyle )
2434 GDK_NOTE (MISC, g_print ("update_style_bits: %p: no change\n",
2435 GDK_WINDOW_HWND (window)));
2439 if (old_style != new_style)
2441 GDK_NOTE (MISC, g_print ("update_style_bits: %p: STYLE: %s => %s\n",
2442 GDK_WINDOW_HWND (window),
2443 _gdk_win32_window_style_to_string (old_style),
2444 _gdk_win32_window_style_to_string (new_style)));
2446 SetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE, new_style);
2449 if (old_exstyle != new_exstyle)
2451 GDK_NOTE (MISC, g_print ("update_style_bits: %p: EXSTYLE: %s => %s\n",
2452 GDK_WINDOW_HWND (window),
2453 _gdk_win32_window_exstyle_to_string (old_exstyle),
2454 _gdk_win32_window_exstyle_to_string (new_exstyle)));
2456 SetWindowLong (GDK_WINDOW_HWND (window), GWL_EXSTYLE, new_exstyle);
2459 AdjustWindowRectEx (&after, new_style, FALSE, new_exstyle);
2461 GetWindowRect (GDK_WINDOW_HWND (window), &rect);
2462 rect.left += after.left - before.left;
2463 rect.top += after.top - before.top;
2464 rect.right += after.right - before.right;
2465 rect.bottom += after.bottom - before.bottom;
2467 SetWindowPos (GDK_WINDOW_HWND (window), NULL,
2468 rect.left, rect.top,
2469 rect.right - rect.left, rect.bottom - rect.top,
2470 SWP_FRAMECHANGED | SWP_NOACTIVATE |
2471 SWP_NOREPOSITION | SWP_NOZORDER);
2476 update_single_system_menu_entry (HMENU hmenu,
2481 /* all controls the interpretation of gdk_bit -- if all is TRUE,
2482 * gdk_bit indicates whether menu entry is disabled; if all is
2483 * FALSE, gdk bit indicate whether menu entry is enabled
2485 if ((!all && gdk_bit) || (all && !gdk_bit))
2486 EnableMenuItem (hmenu, menu_entry, MF_BYCOMMAND | MF_ENABLED);
2488 EnableMenuItem (hmenu, menu_entry, MF_BYCOMMAND | MF_GRAYED);
2492 update_system_menu (GdkWindow *window)
2494 GdkWMFunction functions;
2497 if (_gdk_window_get_functions (window, &functions))
2499 HMENU hmenu = GetSystemMenu (GDK_WINDOW_HWND (window), FALSE);
2501 all = (functions & GDK_FUNC_ALL);
2502 update_single_system_menu_entry (hmenu, all, functions & GDK_FUNC_RESIZE, SC_SIZE);
2503 update_single_system_menu_entry (hmenu, all, functions & GDK_FUNC_MOVE, SC_MOVE);
2504 update_single_system_menu_entry (hmenu, all, functions & GDK_FUNC_MINIMIZE, SC_MINIMIZE);
2505 update_single_system_menu_entry (hmenu, all, functions & GDK_FUNC_MAXIMIZE, SC_MAXIMIZE);
2506 update_single_system_menu_entry (hmenu, all, functions & GDK_FUNC_CLOSE, SC_CLOSE);
2511 get_decorations_quark ()
2513 static GQuark quark = 0;
2516 quark = g_quark_from_static_string ("gdk-window-decorations");
2522 gdk_window_set_decorations (GdkWindow *window,
2523 GdkWMDecoration decorations)
2525 GdkWMDecoration* decorations_copy;
2527 g_return_if_fail (GDK_IS_WINDOW (window));
2529 GDK_NOTE (MISC, g_print ("gdk_window_set_decorations: %p: %s %s%s%s%s%s%s\n",
2530 GDK_WINDOW_HWND (window),
2531 (decorations & GDK_DECOR_ALL ? "clearing" : "setting"),
2532 (decorations & GDK_DECOR_BORDER ? "BORDER " : ""),
2533 (decorations & GDK_DECOR_RESIZEH ? "RESIZEH " : ""),
2534 (decorations & GDK_DECOR_TITLE ? "TITLE " : ""),
2535 (decorations & GDK_DECOR_MENU ? "MENU " : ""),
2536 (decorations & GDK_DECOR_MINIMIZE ? "MINIMIZE " : ""),
2537 (decorations & GDK_DECOR_MAXIMIZE ? "MAXIMIZE " : "")));
2539 decorations_copy = g_malloc (sizeof (GdkWMDecoration));
2540 *decorations_copy = decorations;
2541 g_object_set_qdata_full (G_OBJECT (window), get_decorations_quark (), decorations_copy, g_free);
2543 update_style_bits (window);
2547 gdk_window_get_decorations (GdkWindow *window,
2548 GdkWMDecoration *decorations)
2550 GdkWMDecoration* decorations_set;
2552 g_return_val_if_fail (GDK_IS_WINDOW (window), FALSE);
2554 decorations_set = g_object_get_qdata (G_OBJECT (window), get_decorations_quark ());
2555 if (decorations_set)
2556 *decorations = *decorations_set;
2558 return (decorations_set != NULL);
2562 get_functions_quark ()
2564 static GQuark quark = 0;
2567 quark = g_quark_from_static_string ("gdk-window-functions");
2573 gdk_window_set_functions (GdkWindow *window,
2574 GdkWMFunction functions)
2576 GdkWMFunction* functions_copy;
2578 g_return_if_fail (GDK_IS_WINDOW (window));
2580 GDK_NOTE (MISC, g_print ("gdk_window_set_functions: %p: %s %s%s%s%s%s\n",
2581 GDK_WINDOW_HWND (window),
2582 (functions & GDK_FUNC_ALL ? "clearing" : "setting"),
2583 (functions & GDK_FUNC_RESIZE ? "RESIZE " : ""),
2584 (functions & GDK_FUNC_MOVE ? "MOVE " : ""),
2585 (functions & GDK_FUNC_MINIMIZE ? "MINIMIZE " : ""),
2586 (functions & GDK_FUNC_MAXIMIZE ? "MAXIMIZE " : ""),
2587 (functions & GDK_FUNC_CLOSE ? "CLOSE " : "")));
2589 functions_copy = g_malloc (sizeof (GdkWMFunction));
2590 *functions_copy = functions;
2591 g_object_set_qdata_full (G_OBJECT (window), get_functions_quark (), functions_copy, g_free);
2593 update_system_menu (window);
2597 _gdk_window_get_functions (GdkWindow *window,
2598 GdkWMFunction *functions)
2600 GdkWMDecoration* functions_set;
2602 functions_set = g_object_get_qdata (G_OBJECT (window), get_functions_quark ());
2604 *functions = *functions_set;
2606 return (functions_set != NULL);
2610 gdk_win32_window_set_static_gravities (GdkWindow *window,
2611 gboolean use_static)
2613 g_return_val_if_fail (GDK_IS_WINDOW (window), FALSE);
2619 gdk_window_begin_resize_drag (GdkWindow *window,
2628 g_return_if_fail (GDK_IS_WINDOW (window));
2630 if (GDK_WINDOW_DESTROYED (window))
2633 /* Tell Windows to start interactively resizing the window by pretending that
2634 * the left pointer button was clicked in the suitable edge or corner. This
2635 * will only work if the button is down when this function is called, and
2636 * will only work with button 1 (left), since Windows only allows window
2637 * dragging using the left mouse button.
2642 /* Must break the automatic grab that occured when the button was
2643 * pressed, otherwise it won't work.
2645 gdk_display_pointer_ungrab (_gdk_display, 0);
2649 case GDK_WINDOW_EDGE_NORTH_WEST:
2650 winedge = HTTOPLEFT;
2653 case GDK_WINDOW_EDGE_NORTH:
2657 case GDK_WINDOW_EDGE_NORTH_EAST:
2658 winedge = HTTOPRIGHT;
2661 case GDK_WINDOW_EDGE_WEST:
2665 case GDK_WINDOW_EDGE_EAST:
2669 case GDK_WINDOW_EDGE_SOUTH_WEST:
2670 winedge = HTBOTTOMLEFT;
2673 case GDK_WINDOW_EDGE_SOUTH:
2677 case GDK_WINDOW_EDGE_SOUTH_EAST:
2679 winedge = HTBOTTOMRIGHT;
2683 DefWindowProcW (GDK_WINDOW_HWND (window), WM_NCLBUTTONDOWN, winedge,
2684 MAKELPARAM (root_x - _gdk_offset_x, root_y - _gdk_offset_y));
2688 gdk_window_begin_move_drag (GdkWindow *window,
2694 g_return_if_fail (GDK_IS_WINDOW (window));
2696 if (GDK_WINDOW_DESTROYED (window))
2699 /* Tell Windows to start interactively moving the window by pretending that
2700 * the left pointer button was clicked in the titlebar. This will only work
2701 * if the button is down when this function is called, and will only work
2702 * with button 1 (left), since Windows only allows window dragging using the
2703 * left mouse button.
2708 /* Must break the automatic grab that occured when the button was pressed,
2709 * otherwise it won't work.
2711 gdk_display_pointer_ungrab (_gdk_display, 0);
2713 DefWindowProcW (GDK_WINDOW_HWND (window), WM_NCLBUTTONDOWN, HTCAPTION,
2714 MAKELPARAM (root_x - _gdk_offset_x, root_y - _gdk_offset_y));
2719 * Setting window states
2722 gdk_window_iconify (GdkWindow *window)
2724 HWND old_active_window;
2726 g_return_if_fail (GDK_IS_WINDOW (window));
2728 if (GDK_WINDOW_DESTROYED (window))
2731 GDK_NOTE (MISC, g_print ("gdk_window_iconify: %p: %s\n",
2732 GDK_WINDOW_HWND (window),
2733 _gdk_win32_window_state_to_string (((GdkWindowObject *) window)->state)));
2735 if (GDK_WINDOW_IS_MAPPED (window))
2737 old_active_window = GetActiveWindow ();
2738 ShowWindow (GDK_WINDOW_HWND (window), SW_MINIMIZE);
2739 if (old_active_window != GDK_WINDOW_HWND (window))
2740 SetActiveWindow (old_active_window);
2744 gdk_synthesize_window_state (window,
2746 GDK_WINDOW_STATE_ICONIFIED);
2751 gdk_window_deiconify (GdkWindow *window)
2753 g_return_if_fail (GDK_IS_WINDOW (window));
2755 if (GDK_WINDOW_DESTROYED (window))
2758 GDK_NOTE (MISC, g_print ("gdk_window_deiconify: %p: %s\n",
2759 GDK_WINDOW_HWND (window),
2760 _gdk_win32_window_state_to_string (((GdkWindowObject *) window)->state)));
2762 if (GDK_WINDOW_IS_MAPPED (window))
2764 show_window_internal (window, FALSE, TRUE);
2768 gdk_synthesize_window_state (window,
2769 GDK_WINDOW_STATE_ICONIFIED,
2775 gdk_window_stick (GdkWindow *window)
2777 g_return_if_fail (GDK_IS_WINDOW (window));
2779 if (GDK_WINDOW_DESTROYED (window))
2782 /* FIXME: Do something? */
2786 gdk_window_unstick (GdkWindow *window)
2788 g_return_if_fail (GDK_IS_WINDOW (window));
2790 if (GDK_WINDOW_DESTROYED (window))
2793 /* FIXME: Do something? */
2797 gdk_window_maximize (GdkWindow *window)
2799 g_return_if_fail (GDK_IS_WINDOW (window));
2801 if (GDK_WINDOW_DESTROYED (window))
2804 GDK_NOTE (MISC, g_print ("gdk_window_maximize: %p: %s\n",
2805 GDK_WINDOW_HWND (window),
2806 _gdk_win32_window_state_to_string (((GdkWindowObject *) window)->state)));
2808 if (GDK_WINDOW_IS_MAPPED (window))
2809 ShowWindow (GDK_WINDOW_HWND (window), SW_MAXIMIZE);
2811 gdk_synthesize_window_state (window,
2813 GDK_WINDOW_STATE_MAXIMIZED);
2817 gdk_window_unmaximize (GdkWindow *window)
2819 g_return_if_fail (GDK_IS_WINDOW (window));
2821 if (GDK_WINDOW_DESTROYED (window))
2824 GDK_NOTE (MISC, g_print ("gdk_window_unmaximize: %p: %s\n",
2825 GDK_WINDOW_HWND (window),
2826 _gdk_win32_window_state_to_string (((GdkWindowObject *) window)->state)));
2828 if (GDK_WINDOW_IS_MAPPED (window))
2829 ShowWindow (GDK_WINDOW_HWND (window), SW_RESTORE);
2831 gdk_synthesize_window_state (window,
2832 GDK_WINDOW_STATE_MAXIMIZED,
2836 typedef struct _FullscreenInfo FullscreenInfo;
2838 struct _FullscreenInfo
2846 gdk_window_fullscreen (GdkWindow *window)
2848 gint x, y, width, height;
2850 GdkWindowObject *private = (GdkWindowObject *) window;
2854 g_return_if_fail (GDK_IS_WINDOW (window));
2856 fi = g_new (FullscreenInfo, 1);
2858 if (!GetWindowRect (GDK_WINDOW_HWND (window), &(fi->r)))
2862 GdkWindowImplWin32 *impl = GDK_WINDOW_IMPL_WIN32 (private->impl);
2864 monitor = MonitorFromWindow (GDK_WINDOW_HWND (window), MONITOR_DEFAULTTONEAREST);
2865 mi.cbSize = sizeof (mi);
2866 if (monitor && GetMonitorInfo (monitor, &mi))
2868 x = mi.rcMonitor.left;
2869 y = mi.rcMonitor.top;
2870 width = mi.rcMonitor.right - x;
2871 height = mi.rcMonitor.bottom - y;
2876 width = GetSystemMetrics (SM_CXSCREEN);
2877 height = GetSystemMetrics (SM_CYSCREEN);
2880 /* remember for restoring */
2881 fi->hint_flags = impl->hint_flags;
2882 impl->hint_flags &= ~GDK_HINT_MAX_SIZE;
2883 g_object_set_data (G_OBJECT (window), "fullscreen-info", fi);
2884 fi->style = GetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE);
2886 SetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE,
2887 (fi->style & ~WS_OVERLAPPEDWINDOW) | WS_POPUP);
2889 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window), HWND_TOP,
2890 x, y, width, height,
2891 SWP_NOCOPYBITS | SWP_SHOWWINDOW));
2893 gdk_synthesize_window_state (window, 0, GDK_WINDOW_STATE_FULLSCREEN);
2898 gdk_window_unfullscreen (GdkWindow *window)
2901 GdkWindowObject *private = (GdkWindowObject *) window;
2903 g_return_if_fail (GDK_IS_WINDOW (window));
2905 fi = g_object_get_data (G_OBJECT (window), "fullscreen-info");
2908 GdkWindowImplWin32 *impl = GDK_WINDOW_IMPL_WIN32 (private->impl);
2910 impl->hint_flags = fi->hint_flags;
2911 SetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE, fi->style);
2912 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window), HWND_NOTOPMOST,
2913 fi->r.left, fi->r.top,
2914 fi->r.right - fi->r.left, fi->r.bottom - fi->r.top,
2915 SWP_NOCOPYBITS | SWP_SHOWWINDOW));
2917 g_object_set_data (G_OBJECT (window), "fullscreen-info", NULL);
2920 gdk_synthesize_window_state (window, GDK_WINDOW_STATE_FULLSCREEN, 0);
2925 gdk_window_set_keep_above (GdkWindow *window,
2928 g_return_if_fail (GDK_IS_WINDOW (window));
2930 if (GDK_WINDOW_DESTROYED (window))
2933 GDK_NOTE (MISC, g_print ("gdk_window_set_keep_above: %p: %s\n",
2934 GDK_WINDOW_HWND (window),
2935 setting ? "YES" : "NO"));
2937 if (GDK_WINDOW_IS_MAPPED (window))
2939 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window),
2940 setting ? HWND_TOPMOST : HWND_NOTOPMOST,
2942 SWP_NOSIZE | SWP_NOMOVE | SWP_NOACTIVATE));
2945 gdk_synthesize_window_state (window,
2946 setting ? GDK_WINDOW_STATE_BELOW : GDK_WINDOW_STATE_ABOVE,
2947 setting ? GDK_WINDOW_STATE_ABOVE : 0);
2951 gdk_window_set_keep_below (GdkWindow *window,
2954 g_return_if_fail (GDK_IS_WINDOW (window));
2956 if (GDK_WINDOW_DESTROYED (window))
2959 GDK_NOTE (MISC, g_print ("gdk_window_set_keep_below: %p: %s\n",
2960 GDK_WINDOW_HWND (window),
2961 setting ? "YES" : "NO"));
2963 if (GDK_WINDOW_IS_MAPPED (window))
2965 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window),
2966 setting ? HWND_BOTTOM : HWND_NOTOPMOST,
2968 SWP_NOSIZE | SWP_NOMOVE | SWP_NOACTIVATE));
2971 gdk_synthesize_window_state (window,
2972 setting ? GDK_WINDOW_STATE_ABOVE : GDK_WINDOW_STATE_BELOW,
2973 setting ? GDK_WINDOW_STATE_BELOW : 0);
2977 gdk_window_focus (GdkWindow *window,
2980 g_return_if_fail (GDK_IS_WINDOW (window));
2982 if (GDK_WINDOW_DESTROYED (window))
2985 GDK_NOTE (MISC, g_print ("gdk_window_focus: %p: %s\n",
2986 GDK_WINDOW_HWND (window),
2987 _gdk_win32_window_state_to_string (((GdkWindowObject *) window)->state)));
2989 if (((GdkWindowObject *) window)->state & GDK_WINDOW_STATE_MAXIMIZED)
2990 ShowWindow (GDK_WINDOW_HWND (window), SW_SHOWMAXIMIZED);
2992 ShowWindow (GDK_WINDOW_HWND (window), SW_SHOWNORMAL);
2993 SetFocus (GDK_WINDOW_HWND (window));
2997 gdk_window_set_modal_hint (GdkWindow *window,
3000 GdkWindowObject *private;
3002 g_return_if_fail (GDK_IS_WINDOW (window));
3004 if (GDK_WINDOW_DESTROYED (window))
3007 GDK_NOTE (MISC, g_print ("gdk_window_set_modal_hint: %p: %s\n",
3008 GDK_WINDOW_HWND (window),
3009 modal ? "YES" : "NO"));
3011 private = (GdkWindowObject*) window;
3013 if (modal == private->modal_hint)
3016 private->modal_hint = modal;
3019 /* Not sure about this one.. -- Cody */
3020 if (GDK_WINDOW_IS_MAPPED (window))
3021 API_CALL (SetWindowPos, (GDK_WINDOW_HWND (window),
3022 modal ? HWND_TOPMOST : HWND_NOTOPMOST,
3024 SWP_NOMOVE | SWP_NOSIZE));
3029 _gdk_push_modal_window (window);
3030 gdk_window_raise (window);
3034 _gdk_remove_modal_window (window);
3041 gdk_window_set_skip_taskbar_hint (GdkWindow *window,
3042 gboolean skips_taskbar)
3044 static GdkWindow *owner = NULL;
3047 g_return_if_fail (GDK_IS_WINDOW (window));
3049 GDK_NOTE (MISC, g_print ("gdk_window_set_skip_taskbar_hint: %p: %s, doing nothing\n",
3050 GDK_WINDOW_HWND (window),
3051 skips_taskbar ? "YES" : "NO"));
3053 // ### TODO: Need to figure out what to do here.
3061 wa.window_type = GDK_WINDOW_TEMP;
3062 wa.wclass = GDK_INPUT_OUTPUT;
3063 wa.width = wa.height = 1;
3065 owner = gdk_window_new_internal (NULL, &wa, 0, TRUE);
3069 SetWindowLongPtr (GDK_WINDOW_HWND (window), GWLP_HWNDPARENT, (LONG_PTR) GDK_WINDOW_HWND (owner));
3071 #if 0 /* Should we also turn off the minimize and maximize buttons? */
3072 SetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE,
3073 GetWindowLong (GDK_WINDOW_HWND (window), GWL_STYLE) & ~(WS_MINIMIZEBOX|WS_MAXIMIZEBOX|WS_SYSMENU));
3075 SetWindowPos (GDK_WINDOW_HWND (window), NULL,
3077 SWP_FRAMECHANGED | SWP_NOACTIVATE | SWP_NOMOVE |
3078 SWP_NOREPOSITION | SWP_NOSIZE | SWP_NOZORDER);
3083 SetWindowLongPtr (GDK_WINDOW_HWND (window), GWLP_HWNDPARENT, 0);
3088 gdk_window_set_skip_pager_hint (GdkWindow *window,
3089 gboolean skips_pager)
3091 g_return_if_fail (GDK_IS_WINDOW (window));
3093 GDK_NOTE (MISC, g_print ("gdk_window_set_skip_pager_hint: %p: %s, doing nothing\n",
3094 GDK_WINDOW_HWND (window),
3095 skips_pager ? "YES" : "NO"));
3099 gdk_window_set_type_hint (GdkWindow *window,
3100 GdkWindowTypeHint hint)
3102 g_return_if_fail (GDK_IS_WINDOW (window));
3104 if (GDK_WINDOW_DESTROYED (window))
3109 static GEnumClass *class = NULL;
3111 class = g_type_class_ref (GDK_TYPE_WINDOW_TYPE_HINT);
3112 g_print ("gdk_window_set_type_hint: %p: %s\n",
3113 GDK_WINDOW_HWND (window),
3114 g_enum_get_value (class, hint)->value_name);
3117 ((GdkWindowImplWin32 *)((GdkWindowObject *)window)->impl)->type_hint = hint;
3119 update_style_bits (window);
3123 gdk_window_get_type_hint (GdkWindow *window)
3125 g_return_val_if_fail (GDK_IS_WINDOW (window), GDK_WINDOW_TYPE_HINT_NORMAL);
3127 if (GDK_WINDOW_DESTROYED (window))
3128 return GDK_WINDOW_TYPE_HINT_NORMAL;
3130 return GDK_WINDOW_IMPL_WIN32 (((GdkWindowObject *) window)->impl)->type_hint;
3134 gdk_win32_window_shape_combine_region (GdkWindow *window,
3135 const cairo_region_t *shape_region,
3139 if (GDK_WINDOW_DESTROYED (window))
3144 GDK_NOTE (MISC, g_print ("gdk_win32_window_shape_combine_region: %p: none\n",
3145 GDK_WINDOW_HWND (window)));
3146 SetWindowRgn (GDK_WINDOW_HWND (window), NULL, TRUE);
3152 hrgn = _gdk_win32_cairo_region_to_hrgn (shape_region, 0, 0);
3154 GDK_NOTE (MISC, g_print ("gdk_win32_window_shape_combine_region: %p: %p\n",
3155 GDK_WINDOW_HWND (window),
3158 do_shape_combine_region (window, hrgn, offset_x, offset_y);
3163 gdk_window_lookup_for_display (GdkDisplay *display,
3164 GdkNativeWindow anid)
3166 g_return_val_if_fail (display == _gdk_display, NULL);
3168 return gdk_window_lookup (anid);
3172 gdk_window_enable_synchronized_configure (GdkWindow *window)
3174 g_return_if_fail (GDK_IS_WINDOW (window));
3178 gdk_window_configure_finished (GdkWindow *window)
3180 g_return_if_fail (GDK_IS_WINDOW (window));
3184 _gdk_windowing_window_beep (GdkWindow *window)
3186 gdk_display_beep (_gdk_display);
3190 gdk_window_set_opacity (GdkWindow *window,
3194 typedef BOOL (*PFN_SetLayeredWindowAttributes) (HWND, COLORREF, BYTE, DWORD);
3195 PFN_SetLayeredWindowAttributes setLayeredWindowAttributes = NULL;
3197 g_return_if_fail (GDK_IS_WINDOW (window));
3198 g_return_if_fail (WINDOW_IS_TOPLEVEL (window));
3200 if (GDK_WINDOW_DESTROYED (window))
3205 else if (opacity > 1)
3208 exstyle = GetWindowLong (GDK_WINDOW_HWND (window), GWL_EXSTYLE);
3210 if (!(exstyle & WS_EX_LAYERED))
3211 API_CALL (SetWindowLong, (GDK_WINDOW_HWND (window),
3213 exstyle | WS_EX_LAYERED));
3215 setLayeredWindowAttributes =
3216 (PFN_SetLayeredWindowAttributes)GetProcAddress (GetModuleHandle ("user32.dll"), "SetLayeredWindowAttributes");
3218 if (setLayeredWindowAttributes)
3220 API_CALL (setLayeredWindowAttributes, (GDK_WINDOW_HWND (window),
3228 _gdk_windowing_get_shape_for_mask (GdkBitmap *mask)
3230 cairo_region_t *region;
3231 HRGN hrgn = _gdk_win32_bitmap_to_hrgn (mask);
3233 region = _gdk_win32_hrgn_to_region (hrgn);
3234 DeleteObject (hrgn);
3240 _gdk_windowing_window_set_composited (GdkWindow *window, gboolean composited)
3245 _gdk_windowing_window_get_shape (GdkWindow *window)
3247 HRGN hrgn = CreateRectRgn (0, 0, 0, 0);
3248 int type = GetWindowRgn (GDK_WINDOW_HWND (window), hrgn);
3250 if (type == SIMPLEREGION || type == COMPLEXREGION)
3252 cairo_region_t *region = _gdk_win32_hrgn_to_region (hrgn);
3254 DeleteObject (hrgn);
3262 _gdk_windowing_window_get_input_shape (GdkWindow *window)
3264 /* CHECK: are these really supposed to be the same? */
3265 return _gdk_windowing_window_get_shape (window);
3269 _gdk_win32_window_queue_antiexpose (GdkWindow *window,
3270 cairo_region_t *area)
3272 HRGN hrgn = _gdk_win32_cairo_region_to_hrgn (area, 0, 0);
3274 GDK_NOTE (EVENTS, g_print ("_gdk_windowing_window_queue_antiexpose: ValidateRgn %p %s\n",
3275 GDK_WINDOW_HWND (window),
3276 _gdk_win32_cairo_region_to_string (area)));
3278 ValidateRgn (GDK_WINDOW_HWND (window), hrgn);
3280 DeleteObject (hrgn);
3285 /* FIXME: Tis function has never been compiled.
3286 * Please make it work. */
3288 _gdk_win32_window_translate (GdkWindow *window,
3289 cairo_region_t *area,
3293 HRGN hrgn = CreateRectRgn (0, 0, 0, 0);
3296 GdkRectangle extents;
3298 cairo_region_get_extents (area, &extents);
3299 hdc = _gdk_win32_drawable_acquire_dc (GDK_DRAWABLE (window));
3300 GDI_CALL (BitBlt, (hdc, extents.x, extents.y, extents.width, extents.height,
3301 hdc, extents.x + dx, extents.y + dy, SRCCOPY));
3303 /* XXX: We probably need to get invalidations for the whole extents and not
3304 * just the area as we BitBlt */
3305 ret = GetUpdateRgn (GDK_WINDOW_HWND (window), hrgn, FALSE);
3307 WIN32_API_FAILED ("GetUpdateRgn");
3308 else if (ret != NULLREGION)
3310 /* Get current updateregion, move any part of it that intersects area by dx,dy */
3311 HRGN update = _gdk_win32_cairo_region_to_hrgn (area, 0, 0);
3312 ret = CombineRgn (update, hrgn, update, RGN_AND);
3314 WIN32_API_FAILED ("CombineRgn");
3315 else if (ret != NULLREGION)
3317 OffsetRgn (update, dx, dy);
3318 API_CALL (InvalidateRgn, (GDK_WINDOW_HWND (window), update, TRUE));
3320 DeleteObject (update);
3322 DeleteObject (hrgn);
3326 gdk_win32_input_shape_combine_region (GdkWindow *window,
3327 const cairo_region_t *shape_region,
3331 if (GDK_WINDOW_DESTROYED (window))
3333 /* CHECK: are these really supposed to be the same? */
3334 gdk_win32_window_shape_combine_region (window, shape_region, offset_x, offset_y);
3338 _gdk_windowing_window_process_updates_recurse (GdkWindow *window,
3339 cairo_region_t *region)
3341 _gdk_window_process_updates_recurse (window, region);
3345 _gdk_windowing_before_process_all_updates (void)
3350 _gdk_windowing_after_process_all_updates (void)
3355 gdk_window_impl_iface_init (GdkWindowImplIface *iface)
3357 iface->show = gdk_win32_window_show;
3358 iface->hide = gdk_win32_window_hide;
3359 iface->withdraw = gdk_win32_window_withdraw;
3360 iface->set_events = gdk_win32_window_set_events;
3361 iface->get_events = gdk_win32_window_get_events;
3362 iface->raise = gdk_win32_window_raise;
3363 iface->lower = gdk_win32_window_lower;
3364 iface->restack_under = gdk_win32_window_restack_under;
3365 iface->restack_toplevel = gdk_win32_window_restack_toplevel;
3366 iface->move_resize = gdk_win32_window_move_resize;
3367 iface->set_background = gdk_win32_window_set_background;
3368 iface->set_back_pixmap = gdk_win32_window_set_back_pixmap;
3369 iface->reparent = gdk_win32_window_reparent;
3370 iface->set_device_cursor = gdk_win32_window_set_device_cursor;
3371 iface->get_geometry = gdk_win32_window_get_geometry;
3372 iface->get_device_state = gdk_window_win32_get_device_state;
3373 iface->get_root_coords = gdk_win32_window_get_root_coords;
3374 iface->shape_combine_region = gdk_win32_window_shape_combine_region;
3375 iface->input_shape_combine_region = gdk_win32_input_shape_combine_region;
3376 iface->get_deskrelative_origin = gdk_win32_window_get_deskrelative_origin;
3377 iface->set_static_gravities = gdk_win32_window_set_static_gravities;
3378 iface->queue_antiexpose = _gdk_win32_window_queue_antiexpose;
3379 iface->translate = _gdk_win32_window_translate;
3380 iface->destroy = _gdk_win32_window_destroy;
3384 gdk_win32_window_is_win32 (GdkWindow *window)
3386 return GDK_WINDOW_IS_WIN32 (window);