[Xfce4-commits] r26691 - xfwm4/branches/xfce_4_4/src
Olivier Fourdan
olivier at xfce.org
Thu Mar 20 23:38:35 CET 2008
Author: olivier
Date: 2008-03-20 22:38:35 +0000 (Thu, 20 Mar 2008)
New Revision: 26691
Modified:
xfwm4/branches/xfce_4_4/src/compositor.c
xfwm4/branches/xfce_4_4/src/display.h
xfwm4/branches/xfce_4_4/src/screen.h
Log:
Backport overlay and compositor support from trunk (Bug #3849)
Modified: xfwm4/branches/xfce_4_4/src/compositor.c
===================================================================
--- xfwm4/branches/xfce_4_4/src/compositor.c 2008-03-19 23:15:50 UTC (rev 26690)
+++ xfwm4/branches/xfce_4_4/src/compositor.c 2008-03-20 22:38:35 UTC (rev 26691)
@@ -16,12 +16,12 @@
xcompmgr - (c) 2003 Keith Packard
metacity - (c) 2003, 2004 Red Hat, Inc.
- xfwm4 - (c) 2005-2006 Olivier Fourdan
+ xfwm4 - (c) 2005-2008 Olivier Fourdan
*/
#ifdef HAVE_CONFIG_H
-#include <config.h>
+#include "config.h"
#endif
#include <X11/Xlib.h>
@@ -70,9 +70,10 @@
#define WIN_NO_SHADOW(cw) ((cw->c) && \
(FLAG_TEST (cw->c->flags, CLIENT_FLAG_FULLSCREEN | CLIENT_FLAG_BELOW) || \
(cw->c->type & (WINDOW_DOCK | WINDOW_DESKTOP))))
+#define WIN_IS_DOCK(cw) (WIN_HAS_CLIENT(cw) && (cw->c->type & WINDOW_DOCK))
#define WIN_IS_OVERRIDE(cw) (cw->attr.override_redirect)
#define WIN_IS_ARGB(cw) (cw->argb)
-#define WIN_IS_OPAQUE(cw) (((cw->opacity == NET_WM_OPAQUE) && !WIN_IS_ARGB(cw)) || (cw->screen_info->overlays))
+#define WIN_IS_OPAQUE(cw) (((cw->opacity == NET_WM_OPAQUE) && !WIN_IS_ARGB(cw)) || (cw->screen_info->wins_unredirected))
#define WIN_IS_NATIVE_OPAQUE(cw) ((cw->native_opacity) && !WIN_IS_ARGB(cw))
#define WIN_IS_FULLSCREEN(cw) ((cw->attr.x <= 0) && \
(cw->attr.y <= 0) && \
@@ -549,7 +550,7 @@
return (None);
}
- shadowPixmap = XCreatePixmap (display_info->dpy, screen_info->xroot,
+ shadowPixmap = XCreatePixmap (display_info->dpy, screen_info->output,
shadowImage->width, shadowImage->height, 8);
if (shadowPixmap == None)
{
@@ -602,7 +603,7 @@
g_return_val_if_fail (render_format != NULL , None);
pixmap = XCreatePixmap (display_info->dpy,
- screen_info->xroot, 1, 1, argb ? 32 : 8);
+ screen_info->output, 1, 1, argb ? 32 : 8);
g_return_val_if_fail (pixmap != None, None);
pa.repeat = TRUE;
@@ -814,7 +815,7 @@
#endif
if (!pixmap)
{
- pixmap = XCreatePixmap (dpy, screen_info->xroot, 1, 1,
+ pixmap = XCreatePixmap (dpy, screen_info->output, 1, 1,
DefaultDepth (dpy, screen_info->screen));
g_return_val_if_fail (pixmap != None, None);
fill = TRUE;
@@ -866,7 +867,7 @@
g_return_val_if_fail (format != NULL, None);
rootPixmap = XCreatePixmap (display_info->dpy,
- screen_info->xroot,
+ screen_info->output,
screen_width, screen_height, depth);
g_return_val_if_fail (rootPixmap != None, None);
@@ -919,21 +920,21 @@
/*
We apply a shadow to the window if:
- - There is no overlay (ie unredirected windows)
- It's a window with a frame and the user asked for shadows under regular
windows,
- it's an override redirect window that is not shaped, not an argb and
the user asked for shadows on so called "popup" windows.
*/
- if (!(screen_info->overlays) &&
- ((screen_info->params->show_popup_shadow &&
+ if ((screen_info->params->show_popup_shadow &&
WIN_IS_OVERRIDE(cw) &&
+ !WIN_IS_FULLSCREEN(cw) &&
!(WIN_IS_ARGB(cw) || WIN_IS_SHAPED(cw))) ||
(screen_info->params->show_frame_shadow &&
!WIN_IS_OVERRIDE(cw) &&
!WIN_NO_SHADOW(cw) &&
- (WIN_HAS_FRAME(cw) || !(WIN_IS_ARGB(cw) || WIN_IS_SHAPED(cw))))))
+ !WIN_IS_DOCK(cw) &&
+ (WIN_HAS_FRAME(cw) || !(WIN_IS_ARGB(cw) || WIN_IS_SHAPED(cw)))))
{
XRectangle sr;
@@ -1083,7 +1084,7 @@
XCompositeUnredirectWindow (display_info->dpy, cw->id, display_info->composite_mode);
XSync (display_info->dpy, FALSE);
- TRACE ("Window 0x%lx unredirected, overlays is %i", cw->id, screen_info->overlays);
+ TRACE ("Window 0x%lx unredirected, wins_unredirected is %i", cw->id, screen_info->wins_unredirected);
}
}
@@ -1124,11 +1125,11 @@
* screen_info->params->frame_opacity
/ (NET_WM_OPAQUE * 100.0);
- cw->alphaBorderPict = solid_picture (screen_info,
- FALSE,
- frame_opacity,
- 0.0, /* red */
- 0.0, /* green */
+ cw->alphaBorderPict = solid_picture (screen_info,
+ FALSE,
+ frame_opacity,
+ 0.0, /* red */
+ 0.0, /* green */
0.0 /* blue */);
}
@@ -1226,7 +1227,6 @@
gint screen_width;
gint screen_height;
gint screen_number;
- Window xroot;
CWindow *cw;
TRACE ("entering paint_all");
@@ -1237,7 +1237,6 @@
screen_width = screen_info->width;
screen_height = screen_info->height;
screen_number = screen_info->screen;
- xroot = screen_info->xroot;
/* Create root buffer if not done yet */
if (screen_info->rootBuffer == None)
@@ -1355,9 +1354,9 @@
if ((cw->opacity != NET_WM_OPAQUE) && !(cw->alphaPict))
{
cw->alphaPict = solid_picture (screen_info, FALSE,
- (double) cw->opacity / NET_WM_OPAQUE,
- 0.0, /* red */
- 0.0, /* green */
+ (double) cw->opacity / NET_WM_OPAQUE,
+ 0.0, /* red */
+ 0.0, /* green */
0.0 /* blue */);
}
XFixesIntersectRegion (dpy, cw->borderClip, cw->borderClip, cw->borderSize);
@@ -1755,28 +1754,43 @@
map_win (CWindow *cw)
{
ScreenInfo *screen_info;
+ DisplayInfo *display_info;
g_return_if_fail (cw != NULL);
- TRACE ("entering map_win 0x%lx", cw->id);
+ TRACE ("entering map_win 0x%lx\n", cw->id);
- cw->viewable = TRUE;
- cw->damaged = FALSE;
+ screen_info = cw->screen_info;
+ display_info = screen_info->display_info;
- screen_info = cw->screen_info;
if (!WIN_IS_REDIRECTED(cw))
{
- screen_info->overlays++;
- TRACE ("Mapping unredirected window 0x%lx, overlays increased to %i", cw->id, screen_info->overlays);
+ /* To be safe, we count only the fullscreen overlays */
+ if (WIN_IS_FULLSCREEN(cw) && WIN_IS_VIEWABLE (cw))
+ {
+ screen_info->wins_unredirected++;
+ }
+#if HAVE_OVERLAYS
+ if ((screen_info->wins_unredirected == 1) && (display_info->have_overlays))
+ {
+ TRACE ("Unmapping overlay window");
+ XUnmapWindow (myScreenGetXDisplay (screen_info), screen_info->overlay);
+ }
+#endif /* HAVE_OVERLAYS */
+ TRACE ("Mapping unredirected window 0x%lx, wins_unredirected increased to %i", cw->id, screen_info->wins_unredirected);
return;
}
+
+ cw->viewable = TRUE;
+ cw->damaged = FALSE;
+
if (!screen_info->params->unredirect_overlays)
{
- TRACE ("Not unredirecting overlays");
+ TRACE ("Not unredirecting wins_unredirected");
return;
}
/* Check for new windows to un-redirect. */
- if (WIN_IS_FULLSCREEN(cw) && WIN_HAS_DAMAGE(cw) && WIN_IS_OVERRIDE(cw) &&
+ if ((WIN_IS_FULLSCREEN(cw) || (screen_info->wins_unredirected > 0)) && WIN_HAS_DAMAGE(cw) && WIN_IS_OVERRIDE(cw) &&
WIN_IS_NATIVE_OPAQUE(cw) && WIN_IS_REDIRECTED(cw) && !WIN_IS_SHAPED(cw))
{
CWindow *top;
@@ -1797,31 +1811,37 @@
unmap_win (CWindow *cw)
{
ScreenInfo *screen_info;
+ DisplayInfo *display_info;
g_return_if_fail (cw != NULL);
TRACE ("entering unmap_win 0x%lx", cw->id);
screen_info = cw->screen_info;
- if (!WIN_IS_REDIRECTED(cw) && (screen_info->overlays > 0))
- {
- screen_info->overlays--;
- TRACE ("Unmapped window 0x%lx, overlays decreased to %i", cw->id, screen_info->overlays);
- }
+ display_info = screen_info->display_info;
- if (!screen_info->overlays)
+ if (!WIN_IS_REDIRECTED(cw) && WIN_IS_FULLSCREEN(cw) && (screen_info->wins_unredirected > 0))
{
- /* Repaint immediately if that was the last unredirected window */
-
- if (!WIN_IS_REDIRECTED(cw))
+ screen_info->wins_unredirected--;
+ TRACE ("Unmapped window 0x%lx, wins_unredirected decreased to %i", cw->id, screen_info->wins_unredirected);
+ if (!screen_info->wins_unredirected)
{
+ /* Restore the overlay if that was the last unredirected window */
+#if HAVE_OVERLAYS
+ if (display_info->have_overlays)
+ {
+ TRACE ("Remapping overlay window");
+ XMapWindow (myScreenGetXDisplay (screen_info), screen_info->overlay);
+ }
+#endif /* HAVE_OVERLAYS */
damage_screen (screen_info);
repair_screen (screen_info);
- }
- else if (WIN_IS_VISIBLE(cw))
- {
- damage_win (cw);
- }
+ }
}
+ else if (WIN_IS_VISIBLE(cw))
+ {
+ damage_win (cw);
+ }
+
cw->viewable = FALSE;
cw->damaged = FALSE;
free_win_data (cw, FALSE);
@@ -1925,7 +1945,11 @@
new->shaped = is_shaped (display_info, id);
new->viewable = (new->attr.map_state == IsViewable);
- if ((new->attr.class != InputOnly) && (id != screen_info->xroot))
+ if ((new->attr.class != InputOnly)
+#if HAVE_OVERLAYS
+ && ((!display_info->have_overlays) || (id != screen_info->overlay))
+#endif
+ && (id != screen_info->output))
{
new->damage = XDamageCreate (display_info->dpy, id, XDamageReportNonEmpty);
}
@@ -2122,7 +2146,10 @@
{
ScreenInfo *screen_info;
- unmap_win (cw);
+ if (WIN_IS_VIEWABLE (cw))
+ {
+ unmap_win (cw);
+ }
screen_info = cw->screen_info;
screen_info->cwindows = g_list_remove (screen_info->cwindows, (gconstpointer) cw);
@@ -2184,7 +2211,7 @@
ScreenInfo *screen_info = myDisplayGetScreenFromRoot (display_info, ev->window);
if ((screen_info) && (screen_info->rootTile))
{
- XClearArea (display_info->dpy, screen_info->xroot, 0, 0, 0, 0, TRUE);
+ XClearArea (display_info->dpy, screen_info->output, 0, 0, 0, 0, TRUE);
XRenderFreePicture (display_info->dpy, screen_info->rootTile);
screen_info->rootTile = None;
add_repair (display_info);
@@ -2413,7 +2440,10 @@
cw = find_cwindow_in_display (display_info, ev->window);
if (cw)
{
- unmap_win (cw);
+ if (WIN_IS_VIEWABLE (cw))
+ {
+ unmap_win (cw);
+ }
}
}
@@ -2650,10 +2680,11 @@
compositorInitDisplay (DisplayInfo *display_info)
{
#ifdef HAVE_COMPOSITOR
-#if HAVE_NAME_WINDOW_PIXMAP
int composite_major, composite_minor;
-#endif
+ composite_major = 0;
+ composite_minor = 0;
+
if (!XCompositeQueryExtension (display_info->dpy,
&display_info->composite_event_base,
&display_info->composite_error_base))
@@ -2666,9 +2697,11 @@
else
{
display_info->have_composite = TRUE;
+ XCompositeQueryVersion (display_info->dpy, &composite_major, &composite_minor);
#if DEBUG
g_print ("composite event base: %i\n", display_info->composite_event_base);
g_print ("composite error base: %i\n", display_info->composite_error_base);
+ g_print ("composite version: %i.%i\n", composite_major, composite_minor);
#endif
}
@@ -2705,7 +2738,7 @@
#if DEBUG
g_print ("fixes event base: %i\n", display_info->fixes_event_base);
g_print ("fixes error base: %i\n", display_info->fixes_error_base);
-#endif
+#endif /* DEBUG */
}
display_info->compositor_idle_id = 0;
@@ -2723,12 +2756,15 @@
display_info->composite_mode = 0;
#if HAVE_NAME_WINDOW_PIXMAP
- XCompositeQueryVersion (display_info->dpy, &composite_major, &composite_minor);
display_info->have_name_window_pixmap = ((composite_major > 0) || (composite_minor >= 2));
-#else
+#else /* HAVE_NAME_WINDOW_PIXMAP */
display_info->have_name_window_pixmap = FALSE;
-#endif
+#endif /* HAVE_NAME_WINDOW_PIXMAP */
+#if HAVE_OVERLAYS
+ display_info->have_overlays = ((composite_major > 0) || (composite_minor >= 3));
+#endif /* HAVE_OVERLAYS */
+
#else /* HAVE_COMPOSITOR */
display_info->enable_compositor = FALSE;
#endif /* HAVE_COMPOSITOR */
@@ -2792,8 +2828,38 @@
return FALSE;
}
+ screen_info->output = screen_info->xroot;
+#if HAVE_OVERLAYS
+ if (display_info->have_overlays)
+ {
+ screen_info->overlay = XCompositeGetOverlayWindow (display_info->dpy, screen_info->xroot);
+ if (screen_info->overlay != None)
+ {
+ XSetWindowAttributes attributes;
+
+ screen_info->root_overlay = XCreateWindow (display_info->dpy, screen_info->overlay,
+ 0, 0, screen_info->width, screen_info->height, 0, screen_info->depth,
+ InputOutput, screen_info->visual, 0, &attributes);
+ XMapWindow (display_info->dpy, screen_info->root_overlay);
+ XRaiseWindow (display_info->dpy, screen_info->overlay);
+ XShapeCombineRectangles (display_info->dpy, screen_info->overlay,
+ ShapeInput, 0, 0, NULL, 0, ShapeSet, Unsorted);
+ XShapeCombineRectangles (display_info->dpy, screen_info->root_overlay,
+ ShapeInput, 0, 0, NULL, 0, ShapeSet, Unsorted);
+ screen_info->output = screen_info->root_overlay;
+ TRACE ("Overlay enabled");
+ }
+ else
+ {
+ /* Something is wrong with overlay support */
+ TRACE ("Cannot get root window overlay, overlay support disabled");
+ display_info->have_overlays = FALSE;
+ }
+ }
+#endif /* HAVE_OVERLAYS */
+
pa.subwindow_mode = IncludeInferiors;
- screen_info->rootPicture = XRenderCreatePicture (display_info->dpy, screen_info->xroot,
+ screen_info->rootPicture = XRenderCreatePicture (display_info->dpy, screen_info->output,
visual_format, CPSubwindowMode, &pa);
if (screen_info->rootPicture == None)
@@ -2807,19 +2873,19 @@
presum_gaussian (screen_info);
screen_info->rootBuffer = None;
/* Change following argb values to play with shadow colors */
- screen_info->blackPicture = solid_picture (screen_info,
- TRUE,
- 1.0, /* alpha */
- 0.0, /* red */
- 0.0, /* green */
+ screen_info->blackPicture = solid_picture (screen_info,
+ TRUE,
+ 1.0, /* alpha */
+ 0.0, /* red */
+ 0.0, /* green */
0.0 /* blue */);
screen_info->rootTile = None;
screen_info->allDamage = None;
screen_info->cwindows = NULL;
screen_info->compositor_active = TRUE;
- screen_info->overlays = 0;
+ screen_info->wins_unredirected = 0;
- XClearArea (display_info->dpy, screen_info->xroot, 0, 0, 0, 0, TRUE);
+ XClearArea (display_info->dpy, screen_info->output, 0, 0, 0, 0, TRUE);
compositorSetCMSelection (screen_info, screen_info->xfwm4_win);
TRACE ("Manual compositing enabled");
@@ -2864,6 +2930,17 @@
screen_info->cwindows = NULL;
TRACE ("Compositor: removed %i window(s) remaining", i);
+#if HAVE_OVERLAYS
+ if (display_info->have_overlays)
+ {
+ XDestroyWindow (display_info->dpy, screen_info->root_overlay);
+ screen_info->root_overlay = None;
+
+ XCompositeReleaseOverlayWindow (display_info->dpy, screen_info->overlay);
+ screen_info->overlay = None;
+ }
+#endif /* HAVE_OVERLAYS */
+
if (screen_info->rootPicture)
{
XRenderFreePicture (display_info->dpy, screen_info->rootPicture);
@@ -2894,7 +2971,7 @@
}
screen_info->gaussianSize = -1;
- screen_info->overlays = 0;
+ screen_info->wins_unredirected = 0;
XCompositeUnredirectSubwindows (display_info->dpy, screen_info->xroot,
display_info->composite_mode);
Modified: xfwm4/branches/xfce_4_4/src/display.h
===================================================================
--- xfwm4/branches/xfce_4_4/src/display.h 2008-03-19 23:15:50 UTC (rev 26690)
+++ xfwm4/branches/xfce_4_4/src/display.h 2008-03-20 22:38:35 UTC (rev 26691)
@@ -48,6 +48,11 @@
#define HAVE_NAME_WINDOW_PIXMAP 1
#endif /* HAVE_NAME_WINDOW_PIXMAP */
#endif /* COMPOSITE_MAJOR > 0 || COMPOSITE_MINOR >= 2 */
+#if COMPOSITE_MAJOR > 0 || COMPOSITE_MINOR >= 3
+#ifndef HAVE_OVERLAYS
+#define HAVE_OVERLAYS 1
+#endif /* HAVE_OVERLAYS */
+#endif /* COMPOSITE_MAJOR > 0 || COMPOSITE_MINOR >= 3 */
#endif /* HAVE_COMPOSITOR */
#include <gtk/gtk.h>
@@ -286,6 +291,10 @@
gboolean have_name_window_pixmap;
#endif /* HAVE_NAME_WINDOW_PIXMAP */
+#if HAVE_OVERLAYS
+ gboolean have_overlays;
+#endif /* HAVE_OVERLAYS */
+
#endif /* HAVE_COMPOSITOR */
};
@@ -331,7 +340,7 @@
Time myDisplayUpdateCurrentTime (DisplayInfo *,
XEvent *);
Time myDisplayGetCurrentTime (DisplayInfo *);
-Time myDisplayGetTime (DisplayInfo *,
+Time myDisplayGetTime (DisplayInfo *,
Time);
Time myDisplayGetLastUserTime (DisplayInfo *);
void myDisplaySetLastUserTime (DisplayInfo *,
Modified: xfwm4/branches/xfce_4_4/src/screen.h
===================================================================
--- xfwm4/branches/xfce_4_4/src/screen.h 2008-03-19 23:15:50 UTC (rev 26690)
+++ xfwm4/branches/xfce_4_4/src/screen.h 2008-03-20 22:38:35 UTC (rev 26691)
@@ -133,8 +133,14 @@
#endif
#ifdef HAVE_COMPOSITOR
+#if HAVE_OVERLAYS
+ Window overlay;
+ Window root_overlay;
+#endif
GList *cwindows;
+ Window output;
+
gaussian_conv *gaussianMap;
gint gaussianSize;
guchar *shadowCorner;
@@ -146,7 +152,7 @@
Picture rootTile;
XserverRegion allDamage;
- guint overlays;
+ guint wins_unredirected;
gboolean compositor_active;
gboolean clipChanged;
#endif /* HAVE_COMPOSITOR */
More information about the Xfce4-commits
mailing list