summaryrefslogtreecommitdiff
path: root/gdk
diff options
context:
space:
mode:
authorCody Russell <bratsche@src.gnome.org>2007-04-30 15:30:38 +0000
committerCody Russell <bratsche@src.gnome.org>2007-04-30 15:30:38 +0000
commitd22d101f9787e492df11d0a48c307a09ea71bf5d (patch)
tree5090010d8a030d6fca9ccc4615677954c1e51aa1 /gdk
parent7e13e7270655c7e9edf80a97a6fc7accd8392a2a (diff)
downloadgdk-pixbuf-d22d101f9787e492df11d0a48c307a09ea71bf5d.tar.gz
Clear correct area
svn path=/branches/gtk-2-10/; revision=17738
Diffstat (limited to 'gdk')
-rw-r--r--gdk/win32/gdkwindow-win32.c151
1 files changed, 147 insertions, 4 deletions
diff --git a/gdk/win32/gdkwindow-win32.c b/gdk/win32/gdkwindow-win32.c
index 1e8dbaf0b..38cf45aca 100644
--- a/gdk/win32/gdkwindow-win32.c
+++ b/gdk/win32/gdkwindow-win32.c
@@ -1446,6 +1446,139 @@ gdk_window_reparent (GdkWindow *window,
_gdk_window_init_position (GDK_WINDOW (window_private));
}
+static void
+erase_background (GdkWindow *window,
+ HDC hdc)
+{
+ HDC bgdc = NULL;
+ HBRUSH hbr = NULL;
+ HPALETTE holdpal = NULL;
+ RECT rect;
+ COLORREF bg;
+ GdkColormap *colormap;
+ GdkColormapPrivateWin32 *colormap_private;
+ int x, y;
+ int x_offset, y_offset;
+
+ if (((GdkWindowObject *) window)->input_only ||
+ ((GdkWindowObject *) window)->bg_pixmap == GDK_NO_BG ||
+ GDK_WINDOW_IMPL_WIN32 (((GdkWindowObject *) window)->impl)->position_info.no_bg)
+ {
+ return;
+ }
+
+ colormap = gdk_drawable_get_colormap (window);
+
+ if (colormap &&
+ (colormap->visual->type == GDK_VISUAL_PSEUDO_COLOR ||
+ colormap->visual->type == GDK_VISUAL_STATIC_COLOR))
+ {
+ int k;
+
+ colormap_private = GDK_WIN32_COLORMAP_DATA (colormap);
+
+ if (!(holdpal = SelectPalette (hdc, colormap_private->hpal, FALSE)))
+ WIN32_GDI_FAILED ("SelectPalette");
+ else if ((k = RealizePalette (hdc)) == GDI_ERROR)
+ WIN32_GDI_FAILED ("RealizePalette");
+ else if (k > 0)
+ GDK_NOTE (COLORMAP, g_print ("erase_background: realized %p: %d colors\n",
+ colormap_private->hpal, k));
+ }
+
+ x_offset = y_offset = 0;
+ while (window && ((GdkWindowObject *) window)->bg_pixmap == GDK_PARENT_RELATIVE_BG)
+ {
+ /* If this window should have the same background as the parent,
+ * fetch the parent. (And if the same goes for the parent, fetch
+ * the grandparent, etc.)
+ */
+ x_offset += ((GdkWindowObject *) window)->x;
+ y_offset += ((GdkWindowObject *) window)->y;
+ window = GDK_WINDOW (((GdkWindowObject *) window)->parent);
+ }
+
+ if (GDK_WINDOW_IMPL_WIN32 (((GdkWindowObject *) window)->impl)->position_info.no_bg)
+ {
+ /* Improves scolling effect, e.g. main buttons of testgtk */
+ return;
+ }
+
+ GetClipBox (hdc, &rect);
+
+ if (((GdkWindowObject *) window)->bg_pixmap == NULL)
+ {
+ bg = _gdk_win32_colormap_color (GDK_DRAWABLE_IMPL_WIN32 (((GdkWindowObject *) window)->impl)->colormap,
+ ((GdkWindowObject *) window)->bg_color.pixel);
+
+ if (!(hbr = CreateSolidBrush (bg)))
+ WIN32_GDI_FAILED ("CreateSolidBrush");
+ else if (!FillRect (hdc, &rect, hbr))
+ WIN32_GDI_FAILED ("FillRect");
+ if (hbr != NULL)
+ DeleteObject (hbr);
+ }
+ else if (((GdkWindowObject *) window)->bg_pixmap != GDK_NO_BG)
+ {
+ GdkPixmap *pixmap = ((GdkWindowObject *) window)->bg_pixmap;
+ GdkPixmapImplWin32 *pixmap_impl = GDK_PIXMAP_IMPL_WIN32 (GDK_PIXMAP_OBJECT (pixmap)->impl);
+
+ if (x_offset == 0 && y_offset == 0 &&
+ pixmap_impl->width <= 8 && pixmap_impl->height <= 8)
+ {
+ if (!(hbr = CreatePatternBrush (GDK_PIXMAP_HBITMAP (pixmap))))
+ WIN32_GDI_FAILED ("CreatePatternBrush");
+ else if (!FillRect (hdc, &rect, hbr))
+ WIN32_GDI_FAILED ("FillRect");
+ if (hbr != NULL)
+ DeleteObject (hbr);
+ }
+ else
+ {
+ HGDIOBJ oldbitmap;
+
+ if (!(bgdc = CreateCompatibleDC (hdc)))
+ {
+ WIN32_GDI_FAILED ("CreateCompatibleDC");
+ return;
+ }
+ if (!(oldbitmap = SelectObject (bgdc, GDK_PIXMAP_HBITMAP (pixmap))))
+ {
+ WIN32_GDI_FAILED ("SelectObject");
+ DeleteDC (bgdc);
+ return;
+ }
+ x = -x_offset;
+ while (x < rect.right)
+ {
+ if (x + pixmap_impl->width >= rect.left)
+ {
+ y = -y_offset;
+ while (y < rect.bottom)
+ {
+ if (y + pixmap_impl->height >= rect.top)
+ {
+ if (!BitBlt (hdc, x, y,
+ pixmap_impl->width, pixmap_impl->height,
+ bgdc, 0, 0, SRCCOPY))
+ {
+ WIN32_GDI_FAILED ("BitBlt");
+ SelectObject (bgdc, oldbitmap);
+ DeleteDC (bgdc);
+ return;
+ }
+ }
+ y += pixmap_impl->height;
+ }
+ }
+ x += pixmap_impl->width;
+ }
+ SelectObject (bgdc, oldbitmap);
+ DeleteDC (bgdc);
+ }
+ }
+}
+
void
_gdk_windowing_window_clear_area (GdkWindow *window,
gint x,
@@ -1472,8 +1605,9 @@ _gdk_windowing_window_clear_area (GdkWindow *window,
GDK_WINDOW_HWND (window),
width, height, x, y));
hdc = GetDC (GDK_WINDOW_HWND (window));
- IntersectClipRect (hdc, x, y, x + width + 1, y + height + 1);
- SendMessage (GDK_WINDOW_HWND (window), WM_ERASEBKGND, (WPARAM) hdc, 0);
+ IntersectClipRect (hdc, x, y, x + width, y + height);
+ erase_background (window, hdc);
+
GDI_CALL (ReleaseDC, (GDK_WINDOW_HWND (window), hdc));
}
}
@@ -1489,6 +1623,7 @@ _gdk_windowing_window_clear_area_e (GdkWindow *window,
if (!GDK_WINDOW_DESTROYED (window))
{
+ HDC hdc;
RECT rect;
GDK_NOTE (MISC, g_print ("_gdk_windowing_window_clear_area_e: %p: "
@@ -1496,10 +1631,18 @@ _gdk_windowing_window_clear_area_e (GdkWindow *window,
GDK_WINDOW_HWND (window),
width, height, x, y));
+ /* The background should be erased before the expose event is
+ generated */
+ hdc = GetDC (GDK_WINDOW_HWND (window));
+ IntersectClipRect (hdc, x, y, x + width, y + height);
+ erase_background (window, hdc);
+ GDI_CALL (ReleaseDC, (GDK_WINDOW_HWND (window), hdc));
+
rect.left = x;
- rect.right = x + width + 1;
+ rect.right = x + width;
rect.top = y;
- rect.bottom = y + height + 1;
+ rect.bottom = y + height;
+
GDI_CALL (InvalidateRect, (GDK_WINDOW_HWND (window), &rect, TRUE));
UpdateWindow (GDK_WINDOW_HWND (window));
}