1 /* GDK - The GIMP Drawing Kit
2 * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
20 /* gdkgeometry-x11.c: emulation of 32 bit coordinates within the
23 * By Owen Taylor <otaylor@redhat.com>
24 * Copyright Red Hat, Inc. 2000
27 #include "gdk.h" /* For gdk_rectangle_intersect */
28 #include "gdkprivate-x11.h"
30 #include "gdkregion.h"
31 #include "gdkinternals.h"
33 typedef struct _GdkWindowQueueItem GdkWindowQueueItem;
34 typedef struct _GdkWindowParentPos GdkWindowParentPos;
37 GDK_WINDOW_QUEUE_TRANSLATE,
38 GDK_WINDOW_QUEUE_ANTIEXPOSE
41 struct _GdkWindowQueueItem
45 GdkWindowQueueType type;
57 struct _GdkWindowParentPos
63 GdkRectangle clip_rect;
66 static void gdk_window_compute_position (GdkWindowImplX11 *window,
67 GdkWindowParentPos *parent_pos,
68 GdkXPositionInfo *info);
69 static void gdk_window_compute_parent_pos (GdkWindowImplX11 *window,
70 GdkWindowParentPos *parent_pos);
71 static void gdk_window_premove (GdkWindow *window,
72 GdkWindowParentPos *parent_pos);
73 static void gdk_window_postmove (GdkWindow *window,
74 GdkWindowParentPos *parent_pos);
75 static void gdk_window_queue_translation (GdkWindow *window,
78 static void gdk_window_tmp_unset_bg (GdkWindow *window);
79 static void gdk_window_tmp_reset_bg (GdkWindow *window);
80 static void gdk_window_clip_changed (GdkWindow *window,
81 GdkRectangle *old_clip,
82 GdkRectangle *new_clip);
84 static GSList *translate_queue = NULL;
87 _gdk_windowing_window_get_offsets (GdkWindow *window,
91 GdkWindowImplX11 *impl =
92 GDK_WINDOW_IMPL_X11 (GDK_WINDOW_OBJECT (window)->impl);
94 *x_offset = impl->position_info.x_offset;
95 *y_offset = impl->position_info.y_offset;
99 _gdk_window_init_position (GdkWindow *window)
101 GdkWindowParentPos parent_pos;
102 GdkWindowImplX11 *impl;
104 g_return_if_fail (GDK_IS_WINDOW (window));
107 GDK_WINDOW_IMPL_X11 (GDK_WINDOW_OBJECT (window)->impl);
109 gdk_window_compute_parent_pos (impl, &parent_pos);
110 gdk_window_compute_position (impl, &parent_pos, &impl->position_info);
115 * @window: a #GdkWindow
116 * @dx: Amount to scroll in the X direction
117 * @dy: Amount to scroll in the Y direction
119 * Scroll the contents of its window, both pixels and children, by
120 * the given amount. Portions of the window that the scroll operation
121 * brings in from offscreen areas are invalidated. The invalidated
122 * region may be bigger than what would strictly be necessary.
123 * (For X11, a minimum area will be invalidated if the window has
124 * no subwindows, or if the edges of the window's parent do not extend
125 * beyond the edges of the window. In other cases, a multi-step process
126 * is used to scroll the window which may produce temporary visual
127 * artifacts and unnecessary invalidations.)
130 gdk_window_scroll (GdkWindow *window,
134 gboolean can_guffaw_scroll = FALSE;
135 GdkWindowImplX11 *impl;
136 GdkWindowObject *obj;
138 g_return_if_fail (GDK_IS_WINDOW (window));
140 obj = GDK_WINDOW_OBJECT (window);
142 impl = GDK_WINDOW_IMPL_X11 (obj->impl);
144 if (GDK_WINDOW_DESTROYED (window))
147 /* Move the current invalid region */
148 if (obj->update_area)
149 gdk_region_offset (obj->update_area, dx, dy);
151 /* We can guffaw scroll if we are a child window, and the parent
152 * does not extend beyond our edges.
155 if (GDK_WINDOW_TYPE (window) == GDK_WINDOW_CHILD)
157 GdkWindowImplX11 *parent_impl = GDK_WINDOW_IMPL_X11 (obj->parent->impl);
158 can_guffaw_scroll = (obj->x <= 0 &&
160 obj->x + impl->width >= parent_impl->width &&
161 obj->y + impl->height >= parent_impl->height);
164 if (!obj->children || !can_guffaw_scroll)
166 /* Use XCopyArea, then move any children later
169 GdkRegion *invalidate_region;
170 GdkRectangle dest_rect;
172 invalidate_region = gdk_region_rectangle (&impl->position_info.clip_rect);
174 dest_rect = impl->position_info.clip_rect;
177 gdk_rectangle_intersect (&dest_rect, &impl->position_info.clip_rect, &dest_rect);
179 if (dest_rect.width > 0 && dest_rect.height > 0)
183 GdkRegion *tmp_region;
185 tmp_region = gdk_region_rectangle (&dest_rect);
186 gdk_region_subtract (invalidate_region, tmp_region);
187 gdk_region_destroy (tmp_region);
189 gdk_window_queue_translation (window, dx, dy);
191 values.graphics_exposures = True;
192 gc = XCreateGC (GDK_WINDOW_XDISPLAY (window),
193 GDK_WINDOW_XID (window),
194 GCGraphicsExposures, &values);
196 XCopyArea (GDK_WINDOW_XDISPLAY (window),
197 GDK_WINDOW_XID (window),
198 GDK_WINDOW_XID (window),
200 dest_rect.x - dx, dest_rect.y - dy,
201 dest_rect.width, dest_rect.height,
202 dest_rect.x, dest_rect.y);
204 XFreeGC (GDK_WINDOW_XDISPLAY (window), gc);
207 gdk_window_invalidate_region (window, invalidate_region, TRUE);
208 gdk_region_destroy (invalidate_region);
210 tmp_list = obj->children;
213 GdkWindow * child = GDK_WINDOW (tmp_list->data);
215 gdk_window_move (child, obj->x + dx, obj->y + dy);
217 tmp_list = tmp_list->next;
224 g_warning ("gdk_window_scroll(): guffaw scrolling not yet implemented");
229 _gdk_window_move_resize_child (GdkWindow *window,
235 GdkWindowImplX11 *impl;
236 GdkWindowObject *obj;
237 GdkXPositionInfo new_info;
238 GdkWindowParentPos parent_pos;
241 gint d_xoffset, d_yoffset;
246 g_return_if_fail (window != NULL);
247 g_return_if_fail (GDK_IS_WINDOW (window));
249 impl = GDK_WINDOW_IMPL_X11 (GDK_WINDOW_OBJECT (window)->impl);
250 obj = GDK_WINDOW_OBJECT (window);
255 is_move = dx != 0 || dy != 0;
256 is_resize = impl->width != width || impl->height != height;
258 if (!is_move && !is_resize)
264 impl->height = height;
266 gdk_window_compute_parent_pos (impl, &parent_pos);
267 gdk_window_compute_position (impl, &parent_pos, &new_info);
269 gdk_window_clip_changed (window, &impl->position_info.clip_rect, &new_info.clip_rect);
271 parent_pos.x += obj->x;
272 parent_pos.y += obj->y;
273 parent_pos.x11_x += new_info.x;
274 parent_pos.x11_y += new_info.y;
275 parent_pos.clip_rect = new_info.clip_rect;
277 d_xoffset = new_info.x_offset - impl->position_info.x_offset;
278 d_yoffset = new_info.y_offset - impl->position_info.y_offset;
280 if (d_xoffset != 0 || d_yoffset != 0)
282 gint new_x0, new_y0, new_x1, new_y1;
284 gdk_window_set_static_gravities (window, TRUE);
286 if (d_xoffset < 0 || d_yoffset < 0)
287 gdk_window_queue_translation (window, MIN (d_xoffset, 0), MIN (d_yoffset, 0));
291 new_x0 = impl->position_info.x + d_xoffset;
292 new_x1 = impl->position_info.x + impl->position_info.width;
296 new_x0 = impl->position_info.x;
297 new_x1 = impl->position_info.x + new_info.width + d_xoffset;
302 new_y0 = impl->position_info.y + d_yoffset;
303 new_y1 = impl->position_info.y + impl->position_info.height;
307 new_y0 = impl->position_info.y;
308 new_y1 = impl->position_info.y + new_info.height + d_yoffset;
311 XMoveResizeWindow (GDK_WINDOW_XDISPLAY (window),
312 GDK_WINDOW_XID (window),
313 new_x0, new_y0, new_x1 - new_x0, new_y1 - new_y0);
315 tmp_list = obj->children;
318 gdk_window_premove (tmp_list->data, &parent_pos);
319 tmp_list = tmp_list->next;
322 XMoveWindow (GDK_WINDOW_XDISPLAY (window),
323 GDK_WINDOW_XID (window),
324 new_x0 + dx, new_y0 + dy);
326 if (d_xoffset > 0 || d_yoffset > 0)
327 gdk_window_queue_translation (window, MAX (d_xoffset, 0), MAX (d_yoffset, 0));
329 XMoveResizeWindow (GDK_WINDOW_XDISPLAY (window),
330 GDK_WINDOW_XID (window),
331 new_info.x, new_info.y, new_info.width, new_info.height);
333 if (impl->position_info.no_bg)
334 gdk_window_tmp_reset_bg (window);
336 if (!impl->position_info.mapped && new_info.mapped && GDK_WINDOW_IS_MAPPED (obj))
337 XMapWindow (GDK_WINDOW_XDISPLAY (window), GDK_WINDOW_XID (window));
339 impl->position_info = new_info;
341 tmp_list = obj->children;
344 gdk_window_postmove (tmp_list->data, &parent_pos);
345 tmp_list = tmp_list->next;
350 if (is_move && is_resize)
351 gdk_window_set_static_gravities (window, FALSE);
353 if (impl->position_info.mapped && !new_info.mapped)
354 XUnmapWindow (GDK_WINDOW_XDISPLAY (window), GDK_WINDOW_XID (window));
356 tmp_list = obj->children;
359 gdk_window_premove (tmp_list->data, &parent_pos);
360 tmp_list = tmp_list->next;
364 XMoveResizeWindow (GDK_WINDOW_XDISPLAY (window),
365 GDK_WINDOW_XID (window),
366 new_info.x, new_info.y, new_info.width, new_info.height);
368 XMoveWindow (GDK_WINDOW_XDISPLAY (window),
369 GDK_WINDOW_XID (window),
370 new_info.x, new_info.y);
372 tmp_list = obj->children;
375 gdk_window_postmove (tmp_list->data, &parent_pos);
376 tmp_list = tmp_list->next;
379 if (impl->position_info.no_bg)
380 gdk_window_tmp_reset_bg (window);
382 if (!impl->position_info.mapped && new_info.mapped && GDK_WINDOW_IS_MAPPED (obj))
383 XMapWindow (GDK_WINDOW_XDISPLAY (window), GDK_WINDOW_XID (window));
385 impl->position_info = new_info;
390 gdk_window_compute_position (GdkWindowImplX11 *window,
391 GdkWindowParentPos *parent_pos,
392 GdkXPositionInfo *info)
394 GdkWindowObject *wrapper;
398 g_return_if_fail (GDK_IS_WINDOW_IMPL_X11 (window));
400 wrapper = GDK_WINDOW_OBJECT (GDK_DRAWABLE_IMPL_X11 (window)->wrapper);
404 if (window->width <= 32768)
406 info->width = window->width;
407 info->x = parent_pos->x + wrapper->x - parent_pos->x11_x;
413 if (parent_pos->x + wrapper->x < -16384)
415 if (parent_pos->x + wrapper->x + window->width < 16384)
416 info->x = parent_pos->x + wrapper->x + window->width - 32768 - parent_pos->x11_x;
418 info->x = -16384 - parent_pos->x11_y;
421 info->x = parent_pos->x + wrapper->x - parent_pos->x11_x;
424 if (window->height <= 32768)
426 info->height = window->height;
427 info->y = parent_pos->y + wrapper->y - parent_pos->x11_y;
432 info->height = 32768;
433 if (parent_pos->y + wrapper->y < -16384)
435 if (parent_pos->y + wrapper->y + window->height < 16384)
436 info->y = parent_pos->y + wrapper->y + window->height - 32768 - parent_pos->x11_y;
438 info->y = -16384 - parent_pos->x11_y;
441 info->y = parent_pos->y + wrapper->y - parent_pos->x11_y;
444 parent_x_offset = parent_pos->x11_x - parent_pos->x;
445 parent_y_offset = parent_pos->x11_y - parent_pos->y;
447 info->x_offset = parent_x_offset + info->x - wrapper->x;
448 info->y_offset = parent_y_offset + info->y - wrapper->y;
450 /* We don't considering the clipping of toplevel windows and their immediate children
451 * by their parents, and simply always map those windows.
453 if (parent_pos->clip_rect.width == G_MAXINT)
455 /* Check if the window would wrap around into the visible space in either direction */
456 else if (info->x + parent_x_offset < parent_pos->clip_rect.x + parent_pos->clip_rect.width - 65536 ||
457 info->x + info->width + parent_x_offset > parent_pos->clip_rect.x + 65536 ||
458 info->y + parent_y_offset < parent_pos->clip_rect.y + parent_pos->clip_rect.height - 65536 ||
459 info->y + info->height + parent_y_offset > parent_pos->clip_rect.y + 65536)
460 info->mapped = FALSE;
466 if (GDK_WINDOW_TYPE (wrapper) == GDK_WINDOW_CHILD)
468 info->clip_rect.x = wrapper->x;
469 info->clip_rect.y = wrapper->y;
470 info->clip_rect.width = window->width;
471 info->clip_rect.height = window->height;
473 gdk_rectangle_intersect (&info->clip_rect, &parent_pos->clip_rect, &info->clip_rect);
475 info->clip_rect.x -= wrapper->x;
476 info->clip_rect.y -= wrapper->y;
480 info->clip_rect.x = 0;
481 info->clip_rect.y = 0;
482 info->clip_rect.width = G_MAXINT;
483 info->clip_rect.height = G_MAXINT;
488 gdk_window_compute_parent_pos (GdkWindowImplX11 *window,
489 GdkWindowParentPos *parent_pos)
491 GdkWindowObject *wrapper;
492 GdkWindowObject *parent;
493 GdkRectangle tmp_clip;
495 int clip_xoffset = 0;
496 int clip_yoffset = 0;
498 g_return_if_fail (GDK_IS_WINDOW_IMPL_X11 (window));
501 GDK_WINDOW_OBJECT (GDK_DRAWABLE_IMPL_X11 (window)->wrapper);
505 parent_pos->x11_x = 0;
506 parent_pos->x11_y = 0;
508 /* We take a simple approach here and simply consider toplevel
509 * windows not to clip their children on the right/bottom, since the
510 * size of toplevel windows is not directly under our
511 * control. Clipping only really matters when scrolling and
512 * generally we aren't going to be moving the immediate child of a
513 * toplevel beyond the bounds of that toplevel.
515 * We could go ahead and recompute the clips of toplevel windows and
516 * their descendents when we receive size notification, but it would
517 * probably not be an improvement in most cases.
519 parent_pos->clip_rect.x = 0;
520 parent_pos->clip_rect.y = 0;
521 parent_pos->clip_rect.width = G_MAXINT;
522 parent_pos->clip_rect.height = G_MAXINT;
524 parent = (GdkWindowObject *)wrapper->parent;
525 while (parent && parent->window_type == GDK_WINDOW_CHILD)
527 GdkWindowImplX11 *impl = GDK_WINDOW_IMPL_X11 (parent->impl);
529 tmp_clip.x = - clip_xoffset;
530 tmp_clip.y = - clip_yoffset;
531 tmp_clip.width = impl->width;
532 tmp_clip.height = impl->height;
534 gdk_rectangle_intersect (&parent_pos->clip_rect, &tmp_clip, &parent_pos->clip_rect);
536 parent_pos->x += parent->x;
537 parent_pos->y += parent->y;
538 parent_pos->x11_x += impl->position_info.x;
539 parent_pos->x11_y += impl->position_info.y;
541 clip_xoffset += parent->x;
542 clip_yoffset += parent->y;
544 parent = (GdkWindowObject *)parent->parent;
549 gdk_window_premove (GdkWindow *window,
550 GdkWindowParentPos *parent_pos)
552 GdkWindowImplX11 *impl;
553 GdkWindowObject *obj;
554 GdkXPositionInfo new_info;
556 gint d_xoffset, d_yoffset;
557 GdkWindowParentPos this_pos;
559 obj = (GdkWindowObject *) window;
560 impl = GDK_WINDOW_IMPL_X11 (obj->impl);
562 gdk_window_compute_position (impl, parent_pos, &new_info);
564 gdk_window_clip_changed (window, &impl->position_info.clip_rect, &new_info.clip_rect);
566 this_pos.x = parent_pos->x + obj->x;
567 this_pos.y = parent_pos->y + obj->y;
568 this_pos.x11_x = parent_pos->x11_x + new_info.x;
569 this_pos.x11_y = parent_pos->x11_y + new_info.y;
570 this_pos.clip_rect = new_info.clip_rect;
572 if (impl->position_info.mapped && !new_info.mapped)
573 XUnmapWindow (GDK_DRAWABLE_XDISPLAY (window), GDK_DRAWABLE_XID (window));
575 d_xoffset = new_info.x_offset - impl->position_info.x_offset;
576 d_yoffset = new_info.y_offset - impl->position_info.y_offset;
578 if (d_xoffset != 0 || d_yoffset != 0)
580 gint new_x0, new_y0, new_x1, new_y1;
582 if (d_xoffset < 0 || d_yoffset < 0)
583 gdk_window_queue_translation (window, MIN (d_xoffset, 0), MIN (d_yoffset, 0));
587 new_x0 = impl->position_info.x + d_xoffset;
588 new_x1 = impl->position_info.x + impl->position_info.width;
592 new_x0 = impl->position_info.x;
593 new_x1 = impl->position_info.x + new_info.width + d_xoffset;
598 new_y0 = impl->position_info.y + d_yoffset;
599 new_y1 = impl->position_info.y + impl->position_info.height;
603 new_y0 = impl->position_info.y;
604 new_y1 = impl->position_info.y + new_info.height + d_yoffset;
607 XMoveResizeWindow (GDK_DRAWABLE_XDISPLAY (window),
608 GDK_DRAWABLE_XID (window),
609 new_x0, new_y0, new_x1 - new_x0, new_y1 - new_y0);
612 tmp_list = obj->children;
615 gdk_window_premove (tmp_list->data, &this_pos);
616 tmp_list = tmp_list->next;
621 gdk_window_postmove (GdkWindow *window,
622 GdkWindowParentPos *parent_pos)
624 GdkWindowImplX11 *impl;
625 GdkWindowObject *obj;
626 GdkXPositionInfo new_info;
628 gint d_xoffset, d_yoffset;
629 GdkWindowParentPos this_pos;
631 obj = (GdkWindowObject *) window;
632 impl = GDK_WINDOW_IMPL_X11 (obj->impl);
634 gdk_window_compute_position (impl, parent_pos, &new_info);
636 this_pos.x = parent_pos->x + obj->x;
637 this_pos.y = parent_pos->y + obj->y;
638 this_pos.x11_x = parent_pos->x11_x + new_info.x;
639 this_pos.x11_y = parent_pos->x11_y + new_info.y;
640 this_pos.clip_rect = new_info.clip_rect;
642 d_xoffset = new_info.x_offset - impl->position_info.x_offset;
643 d_yoffset = new_info.y_offset - impl->position_info.y_offset;
645 if (d_xoffset != 0 || d_yoffset != 0)
647 if (d_xoffset > 0 || d_yoffset > 0)
648 gdk_window_queue_translation (window, MAX (d_xoffset, 0), MAX (d_yoffset, 0));
650 XMoveResizeWindow (GDK_DRAWABLE_XDISPLAY (window),
651 GDK_DRAWABLE_XID (window),
652 new_info.x, new_info.y, new_info.width, new_info.height);
655 if (!impl->position_info.mapped && new_info.mapped && GDK_WINDOW_IS_MAPPED (obj))
656 XMapWindow (GDK_DRAWABLE_XDISPLAY (window), GDK_DRAWABLE_XID (window));
658 if (impl->position_info.no_bg)
659 gdk_window_tmp_reset_bg (window);
661 impl->position_info = new_info;
663 tmp_list = obj->children;
666 gdk_window_postmove (tmp_list->data, &this_pos);
667 tmp_list = tmp_list->next;
672 gdk_window_queue_translation (GdkWindow *window,
676 GdkWindowQueueItem *item = g_new (GdkWindowQueueItem, 1);
677 item->window = window;
678 item->serial = NextRequest (GDK_WINDOW_XDISPLAY (window));
679 item->type = GDK_WINDOW_QUEUE_TRANSLATE;
680 item->u.translate.dx = dx;
681 item->u.translate.dy = dy;
683 gdk_drawable_ref (window);
684 translate_queue = g_slist_append (translate_queue, item);
688 _gdk_windowing_window_queue_antiexpose (GdkWindow *window,
691 GdkWindowQueueItem *item = g_new (GdkWindowQueueItem, 1);
692 item->window = window;
693 item->serial = NextRequest (GDK_WINDOW_XDISPLAY (window));
694 item->type = GDK_WINDOW_QUEUE_ANTIEXPOSE;
695 item->u.antiexpose.area = area;
697 gdk_drawable_ref (window);
698 translate_queue = g_slist_append (translate_queue, item);
704 _gdk_window_process_expose (GdkWindow *window,
708 GdkWindowImplX11 *impl;
709 GdkRegion *invalidate_region = gdk_region_rectangle (area);
710 GdkRegion *clip_region;
711 GSList *tmp_list = translate_queue;
713 impl = GDK_WINDOW_IMPL_X11 (GDK_WINDOW_OBJECT (window)->impl);
717 GdkWindowQueueItem *item = tmp_list->data;
718 tmp_list = tmp_list->next;
720 if (serial < item->serial)
722 if (item->window == window)
724 if (item->type == GDK_WINDOW_QUEUE_TRANSLATE)
725 gdk_region_offset (invalidate_region, - item->u.translate.dx, - item->u.translate.dy);
726 else /* anti-expose */
727 gdk_region_subtract (invalidate_region, item->u.antiexpose.area);
732 GSList *tmp_link = translate_queue;
734 translate_queue = g_slist_remove_link (translate_queue, translate_queue);
735 gdk_drawable_unref (item->window);
737 if (item->type == GDK_WINDOW_QUEUE_ANTIEXPOSE)
738 gdk_region_destroy (item->u.antiexpose.area);
741 g_slist_free_1 (tmp_link);
745 clip_region = gdk_region_rectangle (&impl->position_info.clip_rect);
746 gdk_region_intersect (invalidate_region, clip_region);
748 if (!gdk_region_empty (invalidate_region))
749 gdk_window_invalidate_region (window, invalidate_region, FALSE);
751 gdk_region_destroy (invalidate_region);
752 gdk_region_destroy (clip_region);
756 gdk_window_tmp_unset_bg (GdkWindow *window)
758 GdkWindowImplX11 *impl;
759 GdkWindowObject *obj;
761 obj = (GdkWindowObject *) window;
762 impl = GDK_WINDOW_IMPL_X11 (obj->impl);
764 impl->position_info.no_bg = TRUE;
766 if (obj->bg_pixmap != GDK_NO_BG)
767 XSetWindowBackgroundPixmap (GDK_DRAWABLE_XDISPLAY (window),
768 GDK_DRAWABLE_XID (window), None);
772 gdk_window_tmp_reset_bg (GdkWindow *window)
774 GdkWindowImplX11 *impl;
775 GdkWindowObject *obj;
777 obj = (GdkWindowObject *) window;
778 impl = GDK_WINDOW_IMPL_X11 (obj->impl);
780 impl->position_info.no_bg = FALSE;
782 if (obj->bg_pixmap == GDK_NO_BG)
789 if (obj->bg_pixmap == GDK_PARENT_RELATIVE_BG)
790 xpixmap = ParentRelative;
792 xpixmap = GDK_DRAWABLE_XID (obj->bg_pixmap);
794 XSetWindowBackgroundPixmap (GDK_DRAWABLE_XDISPLAY (window),
795 GDK_DRAWABLE_XID (window), xpixmap);
799 XSetWindowBackground (GDK_DRAWABLE_XDISPLAY (window),
800 GDK_DRAWABLE_XID (window),
801 obj->bg_color.pixel);
806 gdk_window_clip_changed (GdkWindow *window, GdkRectangle *old_clip, GdkRectangle *new_clip)
808 GdkWindowImplX11 *impl;
809 GdkWindowObject *obj;
810 GdkRegion *old_clip_region;
811 GdkRegion *new_clip_region;
813 if (((GdkWindowObject *)window)->input_only)
816 obj = (GdkWindowObject *) window;
817 impl = GDK_WINDOW_IMPL_X11 (obj->impl);
819 old_clip_region = gdk_region_rectangle (old_clip);
820 new_clip_region = gdk_region_rectangle (new_clip);
822 /* Trim invalid region of window to new clip rectangle
824 if (obj->update_area)
825 gdk_region_intersect (obj->update_area, new_clip_region);
827 /* Invalidate newly exposed portion of window
829 gdk_region_subtract (new_clip_region, old_clip_region);
830 if (!gdk_region_empty (new_clip_region))
832 gdk_window_tmp_unset_bg (window);
833 gdk_window_invalidate_region (window, new_clip_region, FALSE);
836 gdk_region_destroy (new_clip_region);
837 gdk_region_destroy (old_clip_region);