X-Git-Url: http://pileus.org/git/?a=blobdiff_plain;f=gdk%2Fgdkoffscreenwindow.c;h=aed09e0e83097d92756c9a580811a2ae8d408421;hb=HEAD;hp=8a020bbe60a511b260422143733f5d24214ae21e;hpb=0111030586706f91f3271094280ad23559c47b36;p=~andy%2Fgtk diff --git a/gdk/gdkoffscreenwindow.c b/gdk/gdkoffscreenwindow.c index 8a020bbe6..aed09e0e8 100644 --- a/gdk/gdkoffscreenwindow.c +++ b/gdk/gdkoffscreenwindow.c @@ -12,9 +12,7 @@ * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. + * License along with this library. If not, see . */ /* @@ -24,20 +22,13 @@ * GTK+ at ftp://ftp.gtk.org/pub/gtk/. */ -#include -#include -#include "gdk.h" +#include "config.h" + #include "gdkwindow.h" #include "gdkinternals.h" #include "gdkwindowimpl.h" -#include "gdkpixmap.h" -#include "gdkdrawable.h" -#include "gdktypes.h" -#include "gdkscreen.h" -#include "gdkgc.h" -#include "gdkcolor.h" -#include "gdkcursor.h" -#include "gdkalias.h" + +#include /* LIMITATIONS: * @@ -51,20 +42,17 @@ typedef struct _GdkOffscreenWindowClass GdkOffscreenWindowClass; struct _GdkOffscreenWindow { - GdkDrawable parent_instance; + GdkWindowImpl parent_instance; GdkWindow *wrapper; - GdkCursor *cursor; - GdkColormap *colormap; - GdkScreen *screen; - GdkPixmap *pixmap; + cairo_surface_t *surface; GdkWindow *embedder; }; struct _GdkOffscreenWindowClass { - GdkDrawableClass parent_class; + GdkWindowImplClass parent_class; }; #define GDK_TYPE_OFFSCREEN_WINDOW (gdk_offscreen_window_get_type()) @@ -74,14 +62,9 @@ struct _GdkOffscreenWindowClass #define GDK_IS_OFFSCREEN_WINDOW_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GDK_TYPE_OFFSCREEN_WINDOW)) #define GDK_OFFSCREEN_WINDOW_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GDK_TYPE_OFFSCREEN_WINDOW, GdkOffscreenWindowClass)) -static void gdk_offscreen_window_impl_iface_init (GdkWindowImplIface *iface); static void gdk_offscreen_window_hide (GdkWindow *window); -G_DEFINE_TYPE_WITH_CODE (GdkOffscreenWindow, - gdk_offscreen_window, - GDK_TYPE_DRAWABLE, - G_IMPLEMENT_INTERFACE (GDK_TYPE_WINDOW_IMPL, - gdk_offscreen_window_impl_iface_init)); +G_DEFINE_TYPE (GdkOffscreenWindow, gdk_offscreen_window, GDK_TYPE_WINDOW_IMPL) static void @@ -89,12 +72,8 @@ gdk_offscreen_window_finalize (GObject *object) { GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (object); - if (offscreen->cursor) - gdk_cursor_unref (offscreen->cursor); - - offscreen->cursor = NULL; - - gdk_pixmap_unref (offscreen->pixmap); + if (offscreen->surface) + cairo_surface_destroy (offscreen->surface); G_OBJECT_CLASS (gdk_offscreen_window_parent_class)->finalize (object); } @@ -106,21 +85,29 @@ gdk_offscreen_window_init (GdkOffscreenWindow *window) static void gdk_offscreen_window_destroy (GdkWindow *window, - gboolean recursing, - gboolean foreign_destroy) + gboolean recursing, + gboolean foreign_destroy) { - GdkWindowObject *private = GDK_WINDOW_OBJECT (window); - GdkOffscreenWindow *offscreen; - - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); - gdk_offscreen_window_set_embedder (window, NULL); - + if (!recursing) gdk_offscreen_window_hide (window); +} + +static cairo_surface_t * +get_surface (GdkOffscreenWindow *offscreen) +{ + if (! offscreen->surface) + { + GdkWindow *window = offscreen->wrapper; + + g_signal_emit_by_name (window, "create-surface", + window->width, + window->height, + &offscreen->surface); + } - g_object_unref (offscreen->colormap); - offscreen->colormap = NULL; + return offscreen->surface; } static gboolean @@ -141,468 +128,38 @@ is_parent_of (GdkWindow *parent, return FALSE; } -static GdkGC * -gdk_offscreen_window_create_gc (GdkDrawable *drawable, - GdkGCValues *values, - GdkGCValuesMask values_mask) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - - return gdk_gc_new_with_values (offscreen->pixmap, values, values_mask); -} - -static GdkImage* -gdk_offscreen_window_copy_to_image (GdkDrawable *drawable, - GdkImage *image, - gint src_x, - gint src_y, - gint dest_x, - gint dest_y, - gint width, - gint height) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - - return gdk_drawable_copy_to_image (offscreen->pixmap, - image, - src_x, - src_y, - dest_x, dest_y, - width, height); -} - static cairo_surface_t * -gdk_offscreen_window_ref_cairo_surface (GdkDrawable *drawable) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - - return _gdk_drawable_ref_cairo_surface (offscreen->pixmap); -} - -static GdkColormap* -gdk_offscreen_window_get_colormap (GdkDrawable *drawable) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - - return offscreen->colormap; -} - -static void -gdk_offscreen_window_set_colormap (GdkDrawable *drawable, - GdkColormap*colormap) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - - if (colormap && GDK_WINDOW_DESTROYED (offscreen->wrapper)) - return; - - if (offscreen->colormap == colormap) - return; - - if (offscreen->colormap) - g_object_unref (offscreen->colormap); - - offscreen->colormap = colormap; - if (offscreen->colormap) - g_object_ref (offscreen->colormap); -} - - -static gint -gdk_offscreen_window_get_depth (GdkDrawable *drawable) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - - return gdk_drawable_get_depth (offscreen->wrapper); -} - -static GdkDrawable * -gdk_offscreen_window_get_source_drawable (GdkDrawable *drawable) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - - return _gdk_drawable_get_source_drawable (offscreen->pixmap); -} - -static GdkDrawable * -gdk_offscreen_window_get_composite_drawable (GdkDrawable *drawable, - gint x, - gint y, - gint width, - gint height, - gint *composite_x_offset, - gint *composite_y_offset) +gdk_offscreen_window_ref_cairo_surface (GdkWindow *window) { - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); + GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (window->impl); - return g_object_ref (offscreen->pixmap); + return cairo_surface_reference (get_surface (offscreen)); } -static GdkScreen* -gdk_offscreen_window_get_screen (GdkDrawable *drawable) +cairo_surface_t * +_gdk_offscreen_window_create_surface (GdkWindow *offscreen, + gint width, + gint height) { - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); + cairo_surface_t *similar; + cairo_surface_t *surface; - return offscreen->screen; -} + g_return_val_if_fail (GDK_IS_OFFSCREEN_WINDOW (offscreen->impl), NULL); -static GdkVisual* -gdk_offscreen_window_get_visual (GdkDrawable *drawable) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); + similar = _gdk_window_ref_cairo_surface (offscreen->parent); - return gdk_drawable_get_visual (offscreen->wrapper); -} + surface = cairo_surface_create_similar (similar, CAIRO_CONTENT_COLOR_ALPHA, width, height); -static void -add_damage (GdkOffscreenWindow *offscreen, - int x, int y, - int w, int h) -{ - GdkRectangle rect; - GdkRegion *damage; - - rect.x = x; - rect.y = y; - rect.width = w; - rect.height = h; - - damage = gdk_region_rectangle (&rect); - _gdk_window_add_damage (offscreen->wrapper, damage); - gdk_region_destroy (damage); -} - -static GdkDrawable * -get_real_drawable (GdkOffscreenWindow *offscreen) -{ - GdkPixmapObject *pixmap; - pixmap = (GdkPixmapObject *) offscreen->pixmap; - return GDK_DRAWABLE (pixmap->impl); -} - -static void -gdk_offscreen_window_draw_drawable (GdkDrawable *drawable, - GdkGC *gc, - GdkPixmap *src, - gint xsrc, - gint ysrc, - gint xdest, - gint ydest, - gint width, - gint height, - GdkDrawable *original_src) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - - gdk_draw_drawable (real_drawable, gc, - src, xsrc, ysrc, - xdest, ydest, - width, height); - - add_damage (offscreen, xdest, ydest, width, height); -} - -static void -gdk_offscreen_window_draw_rectangle (GdkDrawable *drawable, - GdkGC *gc, - gboolean filled, - gint x, - gint y, - gint width, - gint height) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - - gdk_draw_rectangle (real_drawable, - gc, filled, x, y, width, height); - - add_damage (offscreen, x, y, width, height); - -} - -static void -gdk_offscreen_window_draw_arc (GdkDrawable *drawable, - GdkGC *gc, - gboolean filled, - gint x, - gint y, - gint width, - gint height, - gint angle1, - gint angle2) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - - gdk_draw_arc (real_drawable, - gc, - filled, - x, - y, - width, - height, - angle1, - angle2); - add_damage (offscreen, x, y, width, height); -} - -static void -gdk_offscreen_window_draw_polygon (GdkDrawable *drawable, - GdkGC *gc, - gboolean filled, - GdkPoint *points, - gint npoints) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - - gdk_draw_polygon (real_drawable, - gc, - filled, - points, - npoints); - - if (npoints > 0) - { - int min_x, min_y, max_x, max_y, i; - - min_x = max_x = points[0].x; - min_y = max_y = points[0].y; - - for (i = 1; i < npoints; i++) - { - min_x = MIN (min_x, points[i].x); - max_x = MAX (max_x, points[i].x); - min_y = MIN (min_y, points[i].y); - max_y = MAX (max_y, points[i].y); - } - - add_damage (offscreen, min_x, min_y, - max_x - min_x, - max_y - min_y); - } -} - -static void -gdk_offscreen_window_draw_text (GdkDrawable *drawable, - GdkFont *font, - GdkGC *gc, - gint x, - gint y, - const gchar *text, - gint text_length) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - GdkWindowObject *private = GDK_WINDOW_OBJECT (offscreen->wrapper); - - gdk_draw_text (real_drawable, - font, - gc, - x, - y, - text, - text_length); - - /* Hard to compute the minimal size, not that often used anyway. */ - add_damage (offscreen, 0, 0, private->width, private->height); -} - -static void -gdk_offscreen_window_draw_text_wc (GdkDrawable *drawable, - GdkFont *font, - GdkGC *gc, - gint x, - gint y, - const GdkWChar *text, - gint text_length) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - GdkWindowObject *private = GDK_WINDOW_OBJECT (offscreen->wrapper); - - gdk_draw_text_wc (real_drawable, - font, - gc, - x, - y, - text, - text_length); - - /* Hard to compute the minimal size, not that often used anyway. */ - add_damage (offscreen, 0, 0, private->width, private->height); -} - -static void -gdk_offscreen_window_draw_points (GdkDrawable *drawable, - GdkGC *gc, - GdkPoint *points, - gint npoints) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - - gdk_draw_points (real_drawable, - gc, - points, - npoints); - - - if (npoints > 0) - { - int min_x, min_y, max_x, max_y, i; - - min_x = max_x = points[0].x; - min_y = max_y = points[0].y; - - for (i = 1; i < npoints; i++) - { - min_x = MIN (min_x, points[i].x); - max_x = MAX (max_x, points[i].x); - min_y = MIN (min_y, points[i].y); - max_y = MAX (max_y, points[i].y); - } - - add_damage (offscreen, min_x, min_y, - max_x - min_x, - max_y - min_y); - } -} - -static void -gdk_offscreen_window_draw_segments (GdkDrawable *drawable, - GdkGC *gc, - GdkSegment *segs, - gint nsegs) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - - gdk_draw_segments (real_drawable, - gc, - segs, - nsegs); - - if (nsegs > 0) - { - int min_x, min_y, max_x, max_y, i; - - min_x = max_x = segs[0].x1; - min_y = max_y = segs[0].y1; - - for (i = 1; i < nsegs; i++) - { - min_x = MIN (min_x, segs[i].x1); - max_x = MAX (max_x, segs[i].x1); - min_x = MIN (min_x, segs[i].x2); - max_x = MAX (max_x, segs[i].x2); - min_y = MIN (min_y, segs[i].y1); - max_y = MAX (max_y, segs[i].y1); - min_y = MIN (min_y, segs[i].y2); - max_y = MAX (max_y, segs[i].y2); - } - - add_damage (offscreen, min_x, min_y, - max_x - min_x, - max_y - min_y); - } - -} - -static void -gdk_offscreen_window_draw_lines (GdkDrawable *drawable, - GdkGC *gc, - GdkPoint *points, - gint npoints) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - GdkWindowObject *private = GDK_WINDOW_OBJECT (offscreen->wrapper); - - gdk_draw_lines (real_drawable, - gc, - points, - npoints); - - /* Hard to compute the minimal size, as we don't know the line - width, and since joins are hard to calculate. - Its not that often used anyway, damage it all */ - add_damage (offscreen, 0, 0, private->width, private->height); -} - -static void -gdk_offscreen_window_draw_image (GdkDrawable *drawable, - GdkGC *gc, - GdkImage *image, - gint xsrc, - gint ysrc, - gint xdest, - gint ydest, - gint width, - gint height) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - - gdk_draw_image (real_drawable, - gc, - image, - xsrc, - ysrc, - xdest, - ydest, - width, - height); - - add_damage (offscreen, xdest, ydest, width, height); -} - - -static void -gdk_offscreen_window_draw_pixbuf (GdkDrawable *drawable, - GdkGC *gc, - GdkPixbuf *pixbuf, - gint src_x, - gint src_y, - gint dest_x, - gint dest_y, - gint width, - gint height, - GdkRgbDither dither, - gint x_dither, - gint y_dither) -{ - GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (drawable); - GdkDrawable *real_drawable = get_real_drawable (offscreen); - - gdk_draw_pixbuf (real_drawable, - gc, - pixbuf, - src_x, - src_y, - dest_x, - dest_y, - width, - height, - dither, - x_dither, - y_dither); - - add_damage (offscreen, dest_x, dest_y, width, height); + cairo_surface_destroy (similar); + return surface; } void _gdk_offscreen_window_new (GdkWindow *window, - GdkScreen *screen, - GdkVisual *visual, GdkWindowAttr *attributes, gint attributes_mask) { - GdkWindowObject *parent_private; - GdkWindowObject *private; GdkOffscreenWindow *offscreen; g_return_if_fail (attributes != NULL); @@ -610,35 +167,12 @@ _gdk_offscreen_window_new (GdkWindow *window, if (attributes->wclass != GDK_INPUT_OUTPUT) return; /* Can't support input only offscreens */ - private = (GdkWindowObject *)window; - - if (private->parent != NULL && GDK_WINDOW_DESTROYED (private->parent)) + if (window->parent != NULL && GDK_WINDOW_DESTROYED (window->parent)) return; - parent_private = (GdkWindowObject*) private->parent; - private->impl = g_object_new (GDK_TYPE_OFFSCREEN_WINDOW, NULL); - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); + window->impl = g_object_new (GDK_TYPE_OFFSCREEN_WINDOW, NULL); + offscreen = GDK_OFFSCREEN_WINDOW (window->impl); offscreen->wrapper = window; - - offscreen->screen = screen; - - if (attributes_mask & GDK_WA_COLORMAP) - offscreen->colormap = g_object_ref (attributes->colormap); - else - { - if (gdk_screen_get_system_visual (screen) == visual) - { - offscreen->colormap = gdk_screen_get_system_colormap (screen); - g_object_ref (offscreen->colormap); - } - else - offscreen->colormap = gdk_colormap_new (visual, FALSE); - } - - offscreen->pixmap = gdk_pixmap_new ((GdkDrawable *)private->parent, - private->width, - private->height, - private->depth); } static gboolean @@ -647,16 +181,13 @@ gdk_offscreen_window_reparent (GdkWindow *window, gint x, gint y) { - GdkWindowObject *private = (GdkWindowObject *)window; - GdkWindowObject *new_parent_private = (GdkWindowObject *)new_parent; - GdkWindowObject *old_parent; - GdkOffscreenWindow *offscreen; + GdkWindow *old_parent; gboolean was_mapped; if (new_parent) { /* No input-output children of input-only windows */ - if (new_parent_private->input_only && !private->input_only) + if (new_parent->input_only && !window->input_only) return FALSE; /* Don't create loops in hierarchy */ @@ -664,40 +195,41 @@ gdk_offscreen_window_reparent (GdkWindow *window, return FALSE; } - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); - was_mapped = GDK_WINDOW_IS_MAPPED (window); gdk_window_hide (window); - if (private->parent) - private->parent->children = g_list_remove (private->parent->children, window); + if (window->parent) + window->parent->children = g_list_remove (window->parent->children, window); - old_parent = private->parent; - private->parent = new_parent_private; - private->x = x; - private->y = y; + old_parent = window->parent; + window->parent = new_parent; + window->x = x; + window->y = y; - if (new_parent_private) - private->parent->children = g_list_prepend (private->parent->children, window); + if (new_parent) + window->parent->children = g_list_prepend (window->parent->children, window); _gdk_synthesize_crossing_events_for_geometry_change (window); if (old_parent) - _gdk_synthesize_crossing_events_for_geometry_change (GDK_WINDOW (old_parent)); + _gdk_synthesize_crossing_events_for_geometry_change (old_parent); return was_mapped; } +static void +gdk_offscreen_window_set_device_cursor (GdkWindow *window, + GdkDevice *device, + GdkCursor *cursor) +{ +} + static void from_embedder (GdkWindow *window, double embedder_x, double embedder_y, double *offscreen_x, double *offscreen_y) { - GdkWindowObject *private; - - private = (GdkWindowObject *)window; - - g_signal_emit_by_name (private->impl_window, + g_signal_emit_by_name (window->impl_window, "from-embedder", embedder_x, embedder_y, offscreen_x, offscreen_y, @@ -709,11 +241,7 @@ to_embedder (GdkWindow *window, double offscreen_x, double offscreen_y, double *embedder_x, double *embedder_y) { - GdkWindowObject *private; - - private = (GdkWindowObject *)window; - - g_signal_emit_by_name (private->impl_window, + g_signal_emit_by_name (window->impl_window, "to-embedder", offscreen_x, offscreen_y, embedder_x, embedder_y, @@ -727,14 +255,13 @@ gdk_offscreen_window_get_root_coords (GdkWindow *window, gint *root_x, gint *root_y) { - GdkWindowObject *private = GDK_WINDOW_OBJECT (window); GdkOffscreenWindow *offscreen; int tmpx, tmpy; tmpx = x; tmpy = y; - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); + offscreen = GDK_OFFSCREEN_WINDOW (window->impl); if (offscreen->embedder) { double dx, dy; @@ -757,48 +284,13 @@ gdk_offscreen_window_get_root_coords (GdkWindow *window, return TRUE; } -static gint -gdk_offscreen_window_get_deskrelative_origin (GdkWindow *window, - gint *x, - gint *y) -{ - GdkWindowObject *private = GDK_WINDOW_OBJECT (window); - GdkOffscreenWindow *offscreen; - int tmpx, tmpy; - - tmpx = 0; - tmpy = 0; - - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); - if (offscreen->embedder) - { - double dx, dy; - gdk_window_get_deskrelative_origin (offscreen->embedder, - &tmpx, &tmpy); - - to_embedder (window, - 0, 0, - &dx, &dy); - tmpx = floor (tmpx + dx + 0.5); - tmpy = floor (tmpy + dy + 0.5); - } - - - if (x) - *x = tmpx; - if (y) - *y = tmpy; - - return TRUE; -} - static gboolean -gdk_offscreen_window_get_pointer (GdkWindow *window, - gint *x, - gint *y, - GdkModifierType *mask) +gdk_offscreen_window_get_device_state (GdkWindow *window, + GdkDevice *device, + gint *x, + gint *y, + GdkModifierType *mask) { - GdkWindowObject *private = GDK_WINDOW_OBJECT (window); GdkOffscreenWindow *offscreen; int tmpx, tmpy; double dtmpx, dtmpy; @@ -808,10 +300,10 @@ gdk_offscreen_window_get_pointer (GdkWindow *window, tmpy = 0; tmpmask = 0; - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); + offscreen = GDK_OFFSCREEN_WINDOW (window->impl); if (offscreen->embedder != NULL) { - gdk_window_get_pointer (offscreen->embedder, &tmpx, &tmpy, &tmpmask); + gdk_window_get_device_position (offscreen->embedder, device, &tmpx, &tmpy, &tmpmask); from_embedder (window, tmpx, tmpy, &dtmpx, &dtmpy); @@ -829,28 +321,28 @@ gdk_offscreen_window_get_pointer (GdkWindow *window, } /** - * gdk_offscreen_window_get_pixmap: + * gdk_offscreen_window_get_surface: * @window: a #GdkWindow * - * Gets the offscreen pixmap that an offscreen window renders into. If - * you need to keep this around over window resizes, you need to add a - * reference to it. + * Gets the offscreen surface that an offscreen window renders into. + * If you need to keep this around over window resizes, you need to + * add a reference to it. * - * Returns: The offscreen pixmap, or NULL if not offscreen - **/ -GdkPixmap * -gdk_offscreen_window_get_pixmap (GdkWindow *window) + * Returns: (transfer none): The offscreen surface, or %NULL if not offscreen + */ +cairo_surface_t * +gdk_offscreen_window_get_surface (GdkWindow *window) { - GdkWindowObject *private = (GdkWindowObject *)window; GdkOffscreenWindow *offscreen; g_return_val_if_fail (GDK_IS_WINDOW (window), FALSE); - if (!GDK_IS_OFFSCREEN_WINDOW (private->impl)) + if (!GDK_IS_OFFSCREEN_WINDOW (window->impl)) return NULL; - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); - return offscreen->pixmap; + offscreen = GDK_OFFSCREEN_WINDOW (window->impl); + + return get_surface (offscreen); } static void @@ -869,60 +361,55 @@ gdk_offscreen_window_lower (GdkWindow *window) static void gdk_offscreen_window_move_resize_internal (GdkWindow *window, - gint x, - gint y, - gint width, - gint height, - gboolean send_expose_events) + gint x, + gint y, + gint width, + gint height, + gboolean send_expose_events) { - GdkWindowObject *private = (GdkWindowObject *)window; GdkOffscreenWindow *offscreen; - gint dx, dy, dw, dh; - GdkGC *gc; - GdkPixmap *old_pixmap; - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); + offscreen = GDK_OFFSCREEN_WINDOW (window->impl); if (width < 1) width = 1; if (height < 1) height = 1; - if (private->destroyed) + if (window->destroyed) return; - dx = x - private->x; - dy = y - private->y; - dw = width - private->width; - dh = height - private->height; + window->x = x; + window->y = y; - private->x = x; - private->y = y; - - if (private->width != width || - private->height != height) + if (window->width != width || + window->height != height) { - private->width = width; - private->height = height; - - old_pixmap = offscreen->pixmap; - offscreen->pixmap = gdk_pixmap_new (GDK_DRAWABLE (old_pixmap), - width, - height, - private->depth); - - gc = _gdk_drawable_get_scratch_gc (offscreen->pixmap, FALSE); - gdk_draw_drawable (offscreen->pixmap, - gc, - old_pixmap, - 0,0, 0, 0, - -1, -1); - g_object_unref (old_pixmap); + window->width = width; + window->height = height; + + if (offscreen->surface) + { + cairo_surface_t *old_surface; + cairo_t *cr; + + old_surface = offscreen->surface; + offscreen->surface = NULL; + + offscreen->surface = get_surface (offscreen); + + cr = cairo_create (offscreen->surface); + cairo_set_source_surface (cr, old_surface, 0, 0); + cairo_paint (cr); + cairo_destroy (cr); + + cairo_surface_destroy (old_surface); + } } - if (GDK_WINDOW_IS_MAPPED (private)) + if (GDK_WINDOW_IS_MAPPED (window)) { - // TODO: Only invalidate new area, i.e. for larger windows + /* TODO: Only invalidate new area, i.e. for larger windows */ gdk_window_invalidate_rect (window, NULL, TRUE); _gdk_synthesize_crossing_events_for_geometry_change (window); } @@ -930,62 +417,54 @@ gdk_offscreen_window_move_resize_internal (GdkWindow *window, static void gdk_offscreen_window_move_resize (GdkWindow *window, - gboolean with_move, - gint x, - gint y, - gint width, - gint height) + gboolean with_move, + gint x, + gint y, + gint width, + gint height) { - GdkWindowObject *private = (GdkWindowObject *)window; - GdkOffscreenWindow *offscreen; - - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); - if (!with_move) { - x = private->x; - y = private->y; + x = window->x; + y = window->y; } if (width < 0) - width = private->width; + width = window->width; if (height < 0) - height = private->height; + height = window->height; - gdk_offscreen_window_move_resize_internal (window, x, y, - width, height, - TRUE); + gdk_offscreen_window_move_resize_internal (window, + x, y, width, height, + TRUE); } static void gdk_offscreen_window_show (GdkWindow *window, gboolean already_mapped) { - GdkWindowObject *private = (GdkWindowObject *)window; + GdkRectangle area = { 0, 0, window->width, window->height }; - gdk_window_clear_area_e (window, 0, 0, - private->width, private->height); + gdk_window_invalidate_rect (window, &area, FALSE); } static void gdk_offscreen_window_hide (GdkWindow *window) { - GdkWindowObject *private; + /* TODO: This needs updating to the new grab world */ +#if 0 GdkOffscreenWindow *offscreen; GdkDisplay *display; g_return_if_fail (window != NULL); - private = (GdkWindowObject*) window; - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); + offscreen = GDK_OFFSCREEN_WINDOW (window->impl); /* May need to break grabs on children */ - display = gdk_drawable_get_display (window); + display = gdk_window_get_display (window); - /* TODO: This needs updating to the new grab world */ -#if 0 if (display->pointer_grab.window != NULL) { if (is_parent_of (window, display->pointer_grab.window)) @@ -1022,53 +501,13 @@ gdk_offscreen_window_set_events (GdkWindow *window, static void gdk_offscreen_window_set_background (GdkWindow *window, - const GdkColor *color) + cairo_pattern_t *pattern) { - GdkWindowObject *private = (GdkWindowObject *)window; - GdkColormap *colormap = gdk_drawable_get_colormap (window); - - private->bg_color = *color; - gdk_colormap_query_color (colormap, private->bg_color.pixel, &private->bg_color); - - if (private->bg_pixmap && - private->bg_pixmap != GDK_PARENT_RELATIVE_BG && - private->bg_pixmap != GDK_NO_BG) - g_object_unref (private->bg_pixmap); - - private->bg_pixmap = NULL; -} - -static void -gdk_offscreen_window_set_back_pixmap (GdkWindow *window, - GdkPixmap *pixmap) -{ - GdkWindowObject *private = (GdkWindowObject *)window; - - if (pixmap && - private->bg_pixmap != GDK_PARENT_RELATIVE_BG && - private->bg_pixmap != GDK_NO_BG && - !gdk_drawable_get_colormap (pixmap)) - { - g_warning ("gdk_window_set_back_pixmap(): pixmap must have a colormap"); - return; - } - - if (private->bg_pixmap && - private->bg_pixmap != GDK_PARENT_RELATIVE_BG && - private->bg_pixmap != GDK_NO_BG) - g_object_unref (private->bg_pixmap); - - private->bg_pixmap = pixmap; - - if (pixmap && - private->bg_pixmap != GDK_PARENT_RELATIVE_BG && - private->bg_pixmap != GDK_NO_BG) - g_object_ref (pixmap); } static void gdk_offscreen_window_shape_combine_region (GdkWindow *window, - const GdkRegion *shape_region, + const cairo_region_t *shape_region, gint offset_x, gint offset_y) { @@ -1076,7 +515,7 @@ gdk_offscreen_window_shape_combine_region (GdkWindow *window, static void gdk_offscreen_window_input_shape_combine_region (GdkWindow *window, - const GdkRegion *shape_region, + const cairo_region_t *shape_region, gint offset_x, gint offset_y) { @@ -1089,175 +528,276 @@ gdk_offscreen_window_set_static_gravities (GdkWindow *window, return TRUE; } -static void -gdk_offscreen_window_set_cursor (GdkWindow *window, - GdkCursor *cursor) -{ - GdkWindowObject *private = (GdkWindowObject *)window; - GdkOffscreenWindow *offscreen; - - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); - - if (offscreen->cursor) - { - gdk_cursor_unref (offscreen->cursor); - offscreen->cursor = NULL; - } - - if (cursor) - offscreen->cursor = gdk_cursor_ref (cursor); - - /* TODO: The cursor is never actually used... */ -} - static void gdk_offscreen_window_get_geometry (GdkWindow *window, gint *x, gint *y, gint *width, - gint *height, - gint *depth) + gint *height) { - GdkWindowObject *private = (GdkWindowObject *)window; - GdkOffscreenWindow *offscreen; - - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); - - g_return_if_fail (window == NULL || GDK_IS_WINDOW (window)); - if (!GDK_WINDOW_DESTROYED (window)) { if (x) - *x = private->x; + *x = window->x; if (y) - *y = private->y; + *y = window->y; if (width) - *width = private->width; + *width = window->width; if (height) - *height = private->height; - if (depth) - *depth = private->depth; + *height = window->height; } } static gboolean gdk_offscreen_window_queue_antiexpose (GdkWindow *window, - GdkRegion *area) + cairo_region_t *area) { return FALSE; } static void -gdk_offscreen_window_queue_translation (GdkWindow *window, - GdkRegion *area, - gint dx, - gint dy) +gdk_offscreen_window_translate (GdkWindow *window, + cairo_region_t *area, + gint dx, + gint dy) +{ + GdkOffscreenWindow *offscreen = GDK_OFFSCREEN_WINDOW (window->impl); + + if (offscreen->surface) + { + cairo_t *cr; + + cr = cairo_create (offscreen->surface); + + area = cairo_region_copy (area); + + gdk_cairo_region (cr, area); + cairo_clip (cr); + + /* NB: This is a self-copy and Cairo doesn't support that yet. + * So we do a litle trick. + */ + cairo_push_group (cr); + + cairo_set_source_surface (cr, offscreen->surface, dx, dy); + cairo_paint (cr); + + cairo_pop_group_to_source (cr); + cairo_paint (cr); + + cairo_destroy (cr); + } + + _gdk_window_add_damage (window, area); +} + +static cairo_surface_t * +gdk_offscreen_window_resize_cairo_surface (GdkWindow *window, + cairo_surface_t *surface, + gint width, + gint height) { + /* No-op. The surface gets resized in + * gdk_offscreen_window_move_resize_internal(). + */ + return surface; } +/** + * gdk_offscreen_window_set_embedder: + * @window: a #GdkWindow + * @embedder: the #GdkWindow that @window gets embedded in + * + * Sets @window to be embedded in @embedder. + * + * To fully embed an offscreen window, in addition to calling this + * function, it is also necessary to handle the #GdkWindow::pick-embedded-child + * signal on the @embedder and the #GdkWindow::to-embedder and + * #GdkWindow::from-embedder signals on @window. + * + * Since: 2.18 + */ void gdk_offscreen_window_set_embedder (GdkWindow *window, GdkWindow *embedder) { - GdkWindowObject *private = (GdkWindowObject *)window; GdkOffscreenWindow *offscreen; g_return_if_fail (GDK_IS_WINDOW (window)); - if (!GDK_IS_OFFSCREEN_WINDOW (private->impl)) + if (!GDK_IS_OFFSCREEN_WINDOW (window->impl)) return; - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); + offscreen = GDK_OFFSCREEN_WINDOW (window->impl); if (embedder) { g_object_ref (embedder); - GDK_WINDOW_OBJECT (embedder)->num_offscreen_children++; + embedder->num_offscreen_children++; } if (offscreen->embedder) { g_object_unref (offscreen->embedder); - GDK_WINDOW_OBJECT (offscreen->embedder)->num_offscreen_children--; + offscreen->embedder->num_offscreen_children--; } offscreen->embedder = embedder; } +/** + * gdk_offscreen_window_get_embedder: + * @window: a #GdkWindow + * + * Gets the window that @window is embedded in. + * + * Returns: (transfer none): the embedding #GdkWindow, or %NULL + * if @window is not an mbedded offscreen window + * + * Since: 2.18 + */ GdkWindow * gdk_offscreen_window_get_embedder (GdkWindow *window) { - GdkWindowObject *private = (GdkWindowObject *)window; GdkOffscreenWindow *offscreen; g_return_val_if_fail (GDK_IS_WINDOW (window), NULL); - if (!GDK_IS_OFFSCREEN_WINDOW (private->impl)) + if (!GDK_IS_OFFSCREEN_WINDOW (window->impl)) return NULL; - offscreen = GDK_OFFSCREEN_WINDOW (private->impl); + offscreen = GDK_OFFSCREEN_WINDOW (window->impl); return offscreen->embedder; } static void -gdk_offscreen_window_class_init (GdkOffscreenWindowClass *klass) +gdk_offscreen_window_do_nothing (GdkWindow *window) { - GdkDrawableClass *drawable_class = GDK_DRAWABLE_CLASS (klass); - GObjectClass *object_class = G_OBJECT_CLASS (klass); +} - object_class->finalize = gdk_offscreen_window_finalize; +static void +gdk_offscreen_window_set_boolean (GdkWindow *window, + gboolean setting) +{ +} + +static void +gdk_offscreen_window_set_string (GdkWindow *window, + const gchar *setting) +{ +} - drawable_class->create_gc = gdk_offscreen_window_create_gc; - drawable_class->_copy_to_image = gdk_offscreen_window_copy_to_image; - drawable_class->ref_cairo_surface = gdk_offscreen_window_ref_cairo_surface; - drawable_class->set_colormap = gdk_offscreen_window_set_colormap; - drawable_class->get_colormap = gdk_offscreen_window_get_colormap; - drawable_class->get_depth = gdk_offscreen_window_get_depth; - drawable_class->get_screen = gdk_offscreen_window_get_screen; - drawable_class->get_visual = gdk_offscreen_window_get_visual; - drawable_class->get_source_drawable = gdk_offscreen_window_get_source_drawable; - drawable_class->get_composite_drawable = gdk_offscreen_window_get_composite_drawable; - - drawable_class->draw_rectangle = gdk_offscreen_window_draw_rectangle; - drawable_class->draw_arc = gdk_offscreen_window_draw_arc; - drawable_class->draw_polygon = gdk_offscreen_window_draw_polygon; - drawable_class->draw_text = gdk_offscreen_window_draw_text; - drawable_class->draw_text_wc = gdk_offscreen_window_draw_text_wc; - drawable_class->draw_drawable = gdk_offscreen_window_draw_drawable; - drawable_class->draw_points = gdk_offscreen_window_draw_points; - drawable_class->draw_segments = gdk_offscreen_window_draw_segments; - drawable_class->draw_lines = gdk_offscreen_window_draw_lines; - drawable_class->draw_image = gdk_offscreen_window_draw_image; - drawable_class->draw_pixbuf = gdk_offscreen_window_draw_pixbuf; +static void +gdk_offscreen_window_set_list (GdkWindow *window, + GList *list) +{ } static void -gdk_offscreen_window_impl_iface_init (GdkWindowImplIface *iface) +gdk_offscreen_window_set_wmfunctions (GdkWindow *window, + GdkWMFunction functions) { - iface->show = gdk_offscreen_window_show; - iface->hide = gdk_offscreen_window_hide; - iface->withdraw = gdk_offscreen_window_withdraw; - iface->raise = gdk_offscreen_window_raise; - iface->lower = gdk_offscreen_window_lower; - iface->move_resize = gdk_offscreen_window_move_resize; - iface->set_background = gdk_offscreen_window_set_background; - iface->set_back_pixmap = gdk_offscreen_window_set_back_pixmap; - iface->get_events = gdk_offscreen_window_get_events; - iface->set_events = gdk_offscreen_window_set_events; - iface->reparent = gdk_offscreen_window_reparent; - iface->set_cursor = gdk_offscreen_window_set_cursor; - iface->get_geometry = gdk_offscreen_window_get_geometry; - iface->shape_combine_region = gdk_offscreen_window_shape_combine_region; - iface->input_shape_combine_region = gdk_offscreen_window_input_shape_combine_region; - iface->set_static_gravities = gdk_offscreen_window_set_static_gravities; - iface->queue_antiexpose = gdk_offscreen_window_queue_antiexpose; - iface->queue_translation = gdk_offscreen_window_queue_translation; - iface->get_root_coords = gdk_offscreen_window_get_root_coords; - iface->get_deskrelative_origin = gdk_offscreen_window_get_deskrelative_origin; - iface->get_pointer = gdk_offscreen_window_get_pointer; - iface->destroy = gdk_offscreen_window_destroy; } -#define __GDK_OFFSCREEN_WINDOW_C__ -#include "gdkaliasdef.c" +static void +gdk_offscreen_window_set_transient_for (GdkWindow *window, + GdkWindow *another) +{ +} + +static void +gdk_offscreen_window_process_updates_recurse (GdkWindow *window, + cairo_region_t *region) +{ + _gdk_window_process_updates_recurse (window, region); +} + +static void +gdk_offscreen_window_class_init (GdkOffscreenWindowClass *klass) +{ + GdkWindowImplClass *impl_class = GDK_WINDOW_IMPL_CLASS (klass); + GObjectClass *object_class = G_OBJECT_CLASS (klass); + + object_class->finalize = gdk_offscreen_window_finalize; + + impl_class->ref_cairo_surface = gdk_offscreen_window_ref_cairo_surface; + impl_class->show = gdk_offscreen_window_show; + impl_class->hide = gdk_offscreen_window_hide; + impl_class->withdraw = gdk_offscreen_window_withdraw; + impl_class->set_events = gdk_offscreen_window_set_events; + impl_class->get_events = gdk_offscreen_window_get_events; + impl_class->raise = gdk_offscreen_window_raise; + impl_class->lower = gdk_offscreen_window_lower; + impl_class->restack_under = NULL; + impl_class->restack_toplevel = NULL; + impl_class->move_resize = gdk_offscreen_window_move_resize; + impl_class->set_background = gdk_offscreen_window_set_background; + impl_class->reparent = gdk_offscreen_window_reparent; + impl_class->set_device_cursor = gdk_offscreen_window_set_device_cursor; + impl_class->get_geometry = gdk_offscreen_window_get_geometry; + impl_class->get_root_coords = gdk_offscreen_window_get_root_coords; + impl_class->get_device_state = gdk_offscreen_window_get_device_state; + impl_class->shape_combine_region = gdk_offscreen_window_shape_combine_region; + impl_class->input_shape_combine_region = gdk_offscreen_window_input_shape_combine_region; + impl_class->set_static_gravities = gdk_offscreen_window_set_static_gravities; + impl_class->queue_antiexpose = gdk_offscreen_window_queue_antiexpose; + impl_class->translate = gdk_offscreen_window_translate; + impl_class->destroy = gdk_offscreen_window_destroy; + impl_class->destroy_foreign = NULL; + impl_class->resize_cairo_surface = gdk_offscreen_window_resize_cairo_surface; + impl_class->get_shape = NULL; + impl_class->get_input_shape = NULL; + impl_class->beep = NULL; + + impl_class->focus = NULL; + impl_class->set_type_hint = NULL; + impl_class->get_type_hint = NULL; + impl_class->set_modal_hint = NULL; + impl_class->set_skip_taskbar_hint = gdk_offscreen_window_set_boolean; + impl_class->set_skip_pager_hint = gdk_offscreen_window_set_boolean; + impl_class->set_urgency_hint = gdk_offscreen_window_set_boolean; + impl_class->set_geometry_hints = NULL; + impl_class->set_title = gdk_offscreen_window_set_string; + impl_class->set_role = gdk_offscreen_window_set_string; + impl_class->set_startup_id = gdk_offscreen_window_set_string; + impl_class->set_transient_for = gdk_offscreen_window_set_transient_for; + impl_class->get_root_origin = NULL; + impl_class->get_frame_extents = NULL; + impl_class->set_override_redirect = NULL; + impl_class->set_accept_focus = NULL; + impl_class->set_focus_on_map = gdk_offscreen_window_set_boolean; + impl_class->set_icon_list = gdk_offscreen_window_set_list; + impl_class->set_icon_name = gdk_offscreen_window_set_string; + impl_class->iconify = gdk_offscreen_window_do_nothing; + impl_class->deiconify = gdk_offscreen_window_do_nothing; + impl_class->stick = gdk_offscreen_window_do_nothing; + impl_class->unstick = gdk_offscreen_window_do_nothing; + impl_class->maximize = gdk_offscreen_window_do_nothing; + impl_class->unmaximize = gdk_offscreen_window_do_nothing; + impl_class->fullscreen = gdk_offscreen_window_do_nothing; + impl_class->unfullscreen = gdk_offscreen_window_do_nothing; + impl_class->set_keep_above = gdk_offscreen_window_set_boolean; + impl_class->set_keep_below = gdk_offscreen_window_set_boolean; + impl_class->get_group = NULL; + impl_class->set_group = NULL; + impl_class->set_decorations = NULL; + impl_class->get_decorations = NULL; + impl_class->set_functions = gdk_offscreen_window_set_wmfunctions; + impl_class->begin_resize_drag = NULL; + impl_class->begin_move_drag = NULL; + impl_class->enable_synchronized_configure = gdk_offscreen_window_do_nothing; + impl_class->configure_finished = NULL; + impl_class->set_opacity = NULL; + impl_class->set_composited = NULL; + impl_class->destroy_notify = NULL; + impl_class->register_dnd = gdk_offscreen_window_do_nothing; + impl_class->drag_begin = NULL; + impl_class->process_updates_recurse = gdk_offscreen_window_process_updates_recurse; + impl_class->sync_rendering = NULL; + impl_class->simulate_key = NULL; + impl_class->simulate_button = NULL; + impl_class->get_property = NULL; + impl_class->change_property = NULL; + impl_class->delete_property = NULL; +}