I've attached the patch since I don't yet have an easy way to make git 
format-patch and kmail play nice together.  The basic idea is during a 
rotate/other cube transform, 'sticky' windows stick to the screen instead of 
being redrawn once per face (its an option, the default is the old behaviour)

Consider this, please, essentially an RFC - this particular behaviour was 
available previously in Beryl, and was (at least according to 
screenshots/casts) widely used.
From 32bbadaa37bb6e9a6627bcfd3e3ba002be7efb6b Mon Sep 17 00:00:00 2001
From: Quinn Storm <[EMAIL PROTECTED](none)>
Date: Sun, 27 May 2007 19:37:50 -0400
Subject: [PATCH] add 'sticky' mode to cube to allow sticky+not-on-bottom windows to stick to the screen when the screen is transformed

---
 include/cube.h |    6 +++-
 plugins/cube.c |   80 +++++++++++++++++++++++++++++++++++++++++++++++++++++++-
 2 files changed, 84 insertions(+), 2 deletions(-)

diff --git a/include/cube.h b/include/cube.h
index e8720e2..8589452 100644
--- a/include/cube.h
+++ b/include/cube.h
@@ -55,7 +55,8 @@ typedef struct _CubeDisplay {
 #define CUBE_SCREEN_OPTION_MIPMAP	      12
 #define CUBE_SCREEN_OPTION_BACKGROUNDS	      13
 #define CUBE_SCREEN_OPTION_ADJUST_IMAGE	      14
-#define CUBE_SCREEN_OPTION_NUM                15
+#define CUBE_SCREEN_OPTION_STUCK_TO_SCREEN    15
+#define CUBE_SCREEN_OPTION_NUM                16
 
 typedef void (*CubeGetRotationProc) (CompScreen *s,
 				     float      *x,
@@ -74,6 +75,7 @@ typedef struct _CubeScreen {
     ApplyScreenTransformProc   applyScreenTransform;
     SetScreenOptionProc	       setScreenOption;
     OutputChangeNotifyProc     outputChangeNotify;
+	PaintWindowProc		paintWindow;
 
     CubeGetRotationProc	      getRotation;
     CubeClearTargetOutputProc clearTargetOutput;
@@ -119,6 +121,8 @@ typedef struct _CubeScreen {
 
     CompTexture *bg;
     int		nBg;
+
+	Bool finalPaint;
 } CubeScreen;
 
 #define GET_CUBE_DISPLAY(d)					 \
diff --git a/plugins/cube.c b/plugins/cube.c
index ed5030b..3b4c897 100644
--- a/plugins/cube.c
+++ b/plugins/cube.c
@@ -38,6 +38,17 @@ static int cubeDisplayPrivateIndex;
 
 #define NUM_OPTIONS(s) (sizeof ((s)->opt) / sizeof (CompOption))
 
+static const CompTransform identity = {
+	{
+		1.0, 0.0, 0.0, 0.0,
+		0.0, 1.0, 0.0, 0.0,
+		0.0, 0.0, 1.0, 0.0,
+		0.0, 0.0, 0.0, 1.0
+	}
+};
+
+
+
 static void
 cubeLoadImg (CompScreen *s,
 	     int	n)
@@ -713,6 +724,9 @@ cubeSetScreenOption (CompPlugin      *plugin,
 	    return TRUE;
 	}
 	break;
+	case CUBE_SCREEN_OPTION_STUCK_TO_SCREEN:
+		return compSetBoolOption(o, value);
+	break;
     default:
 	return compSetScreenOption (screen, o, value);
     }
@@ -803,18 +817,41 @@ cubePaintScreen (CompScreen		 *s,
 
     CUBE_SCREEN (s);
 
+	cs->finalPaint = TRUE;
+
     if (cs->grabIndex)
     {
 	mask &= ~PAINT_SCREEN_REGION_MASK;
 	mask |= PAINT_SCREEN_TRANSFORMED_MASK;
     }
 
+	if (mask & PAINT_SCREEN_TRANSFORMED_MASK)
+		cs->finalPaint=!(cs->opt[CUBE_SCREEN_OPTION_STUCK_TO_SCREEN].value.b);
+
     cs->srcOutput = output;
 
     UNWRAP (cs, s, paintScreen);
     status = (*s->paintScreen) (s, sAttrib, transform, region, output, mask);
     WRAP (cs, s, paintScreen, cubePaintScreen);
 
+	if (!cs->finalPaint)
+	{
+				glPushMatrix();
+				prepareXCoords(s,output,-DEFAULT_Z_CAMERA);
+		cs->finalPaint=TRUE;
+		CompWindow * w;
+		for (w=s->reverseWindows;w;w=w->prev)
+		{
+			if (((w->type & CompWindowTypeDockMask) || (w->state & CompWindowStateStickyMask && !(w->state & CompWindowStateBelowMask)) ||
+						w->attrib.override_redirect) &&
+				(w->mapNum && w->attrib.map_state == IsViewable && !(w->minimized) && !(w->state & CompWindowStateHiddenMask)))
+			{
+				s->paintWindow(w,&w->paint,&identity,&infiniteRegion,0);
+			}
+		}
+				glPopMatrix();
+	}
+
     return status;
 }
 
@@ -841,6 +878,8 @@ cubeMoveViewportAndPaint (CompScreen		  *s,
 {
     CUBE_SCREEN (s);
 
+	Bool save = cs->finalPaint;
+
     if (cs->nOutput > 1)
     {
 	int cubeOutput, dView;
@@ -865,6 +904,9 @@ cubeMoveViewportAndPaint (CompScreen		  *s,
 	/* translate back to compiz output */
 	output = cs->srcOutput = cs->output[cubeOutput];
 
+		if (dView != 0)
+			cs->finalPaint=!(cs->opt[CUBE_SCREEN_OPTION_STUCK_TO_SCREEN].value.b);
+
 	moveScreenViewport (s, -dView, 0, FALSE);
 	(*s->paintTransformedScreen) (s, sAttrib, transform,
 				      &s->outputDev[output].region,
@@ -873,11 +915,15 @@ cubeMoveViewportAndPaint (CompScreen		  *s,
     }
     else
     {
+		if (dx != 0)
+			cs->finalPaint=!(cs->opt[CUBE_SCREEN_OPTION_STUCK_TO_SCREEN].value.b);
+
 	moveScreenViewport (s, dx, 0, FALSE);
 	(*s->paintTransformedScreen) (s, sAttrib, transform, &s->region,
 				      output, mask);
 	moveScreenViewport (s, -dx, 0, FALSE);
     }
+	cs->finalPaint = save;
 }
 
 static void
@@ -922,6 +968,32 @@ cubeClearTargetOutput (CompScreen *s,
     }
 }
 
+static Bool
+cubePaintWindow (CompWindow          *w,
+		const WindowPaintAttrib *attrib,
+		const CompTransform     *transform,
+		Region          region,
+		unsigned int        mask)
+{
+	Bool status;
+
+	CUBE_SCREEN(w->screen);
+
+	if ((w->type & CompWindowTypeDockMask) || (w->state & CompWindowStateStickyMask && !(w->state & CompWindowStateBelowMask)))
+	{
+		if (!cs->finalPaint)
+		{
+			return FALSE;
+		}
+	}
+
+	UNWRAP(cs, w->screen, paintWindow);
+	status = (*w->screen->paintWindow) (w, attrib, transform, region, mask);
+	WRAP(cs, w->screen, paintWindow, cubePaintWindow);
+
+	return status;
+}
+
 static void
 cubePaintTransformedScreen (CompScreen		    *s,
 			    const ScreenPaintAttrib *sAttrib,
@@ -938,6 +1010,9 @@ cubePaintTransformedScreen (CompScreen		    *s,
 
     CUBE_SCREEN (s);
 
+	if (sAttrib->zCamera != -DEFAULT_Z_CAMERA)
+		cs->finalPaint=!(cs->opt[CUBE_SCREEN_OPTION_STUCK_TO_SCREEN].value.b);
+
     hsize = s->hsize * cs->nOutput;
     size  = hsize;
 
@@ -1602,7 +1677,8 @@ static const CompMetadataOptionInfo cubeScreenOptionInfo[] = {
     { "timestep", "float", "<min>0.1</min>", 0, 0 },
     { "mipmap", "bool", 0, 0, 0 },
     { "backgrounds", "list", "<type>string</type>", 0, 0 },
-    { "adjust_image", "bool", 0, 0, 0 }
+    { "adjust_image", "bool", 0, 0, 0 },
+	{ "stuck_to_screen", "bool", 0, 0, 0 },
 };
 
 static Bool
@@ -1691,6 +1767,7 @@ cubeInitScreen (CompPlugin *p,
     WRAP (cs, s, applyScreenTransform, cubeApplyScreenTransform);
     WRAP (cs, s, setScreenOption, cubeSetGlobalScreenOption);
     WRAP (cs, s, outputChangeNotify, cubeOutputChangeNotify);
+	WRAP (cs, s, paintWindow, cubePaintWindow);
 
     return TRUE;
 }
@@ -1712,6 +1789,7 @@ cubeFiniScreen (CompPlugin *p,
     UNWRAP (cs, s, applyScreenTransform);
     UNWRAP (cs, s, setScreenOption);
     UNWRAP (cs, s, outputChangeNotify);
+	UNWRAP(cs, s, paintWindow);
 
     finiTexture (s, &cs->texture);
     finiTexture (s, &cs->sky);
-- 
1.5.1.4

_______________________________________________
compiz mailing list
compiz@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/compiz

Reply via email to