Hi, Thanks for putting these changes in git, it indeed makes more sense than the way I did it first. I re-made the transparent cube patches to work now with this new interface. Tell me what you think about it.
-Roi On 6/1/07, David Reveman <[EMAIL PROTECTED]> wrote:
I had a look at the interface that allows plugins to affect the stacking of windows during rendering. Just adding first, next, prev, etc. function pointers that can be wrapped didn't seem very appropriate as it doesn't make sense to allow plugins to just wrap some of those functions and the overhead from going through the whole wrapping chain every time next or prev is called is unnecessary. I've added a simple window walking interface that should be sufficient. It should be easy to tell how it works from the changes to screen.c and paint.c. We still have to do something about the clip planes, right? I guess a wrap-able setOutputClipPlanes function will do for now. I'll make this change next unless you've got a better idea. It should be fairly easy to properly integrate any 3D window elevation, translucent cube and sticky window mode now that plugins can hook into the cube plugins structures. Just add whatever hooks you need to the cube plugin. -David
From b1106c9cd92cf388f38d9a0f55a3cd3ac1b944c6 Mon Sep 17 00:00:00 2001 From: Roi Cohen <[EMAIL PROTECTED](none)> Date: Tue, 5 Jun 2007 14:37:11 +0300 Subject: [PATCH] cube painting order --- include/cube.h | 20 ++- plugins/cube.c | 419 ++++++++++++++++++++++++++++++++++++-------------------- 2 files changed, 284 insertions(+), 155 deletions(-) diff --git a/include/cube.h b/include/cube.h index f64ddc8..bc44a32 100644 --- a/include/cube.h +++ b/include/cube.h @@ -25,7 +25,7 @@ #include <compiz.h> -#define CUBE_ABIVERSION 20070523 +#define CUBE_ABIVERSION 20070604 #define CUBE_DISPLAY_OPTION_ABI 0 #define CUBE_DISPLAY_OPTION_INDEX 1 @@ -71,6 +71,12 @@ typedef void (*CubePaintTopBottomProc) (CompScreen *s, CompOutput *output, int size); +typedef enum _PaintOrder +{ + BTF = 0, + FTB +} PaintOrder; + typedef struct _CubeScreen { PreparePaintScreenProc preparePaintScreen; DonePaintScreenProc donePaintScreen; @@ -80,6 +86,7 @@ typedef struct _CubeScreen { ApplyScreenTransformProc applyScreenTransform; SetScreenOptionProc setScreenOption; OutputChangeNotifyProc outputChangeNotify; + InitWindowWalkerProc initWindowWalker; CubeGetRotationProc getRotation; CubeClearTargetOutputProc clearTargetOutput; @@ -87,11 +94,12 @@ typedef struct _CubeScreen { CompOption opt[CUBE_SCREEN_OPTION_NUM]; - int invert; - int xrotations; - GLfloat distance; - GLushort color[3]; - GLfloat tc[12]; + int invert; + int xrotations; + PaintOrder paintOrder; + GLfloat distance; + GLushort color[3]; + GLfloat tc[12]; int grabIndex; diff --git a/plugins/cube.c b/plugins/cube.c index df857ad..f28b9f5 100644 --- a/plugins/cube.c +++ b/plugins/cube.c @@ -32,6 +32,37 @@ #include <cube.h> +#define MULTM(x, y, z) \ +z[0] = x[0] * y[0] + x[4] * y[1] + x[8] * y[2] + x[12] * y[3]; \ +z[1] = x[1] * y[0] + x[5] * y[1] + x[9] * y[2] + x[13] * y[3]; \ +z[2] = x[2] * y[0] + x[6] * y[1] + x[10] * y[2] + x[14] * y[3]; \ +z[3] = x[3] * y[0] + x[7] * y[1] + x[11] * y[2] + x[15] * y[3]; \ +z[4] = x[0] * y[4] + x[4] * y[5] + x[8] * y[6] + x[12] * y[7]; \ +z[5] = x[1] * y[4] + x[5] * y[5] + x[9] * y[6] + x[13] * y[7]; \ +z[6] = x[2] * y[4] + x[6] * y[5] + x[10] * y[6] + x[14] * y[7]; \ +z[7] = x[3] * y[4] + x[7] * y[5] + x[11] * y[6] + x[15] * y[7]; \ +z[8] = x[0] * y[8] + x[4] * y[9] + x[8] * y[10] + x[12] * y[11]; \ +z[9] = x[1] * y[8] + x[5] * y[9] + x[9] * y[10] + x[13] * y[11]; \ +z[10] = x[2] * y[8] + x[6] * y[9] + x[10] * y[10] + x[14] * y[11]; \ +z[11] = x[3] * y[8] + x[7] * y[9] + x[11] * y[10] + x[15] * y[11]; \ +z[12] = x[0] * y[12] + x[4] * y[13] + x[8] * y[14] + x[12] * y[15]; \ +z[13] = x[1] * y[12] + x[5] * y[13] + x[9] * y[14] + x[13] * y[15]; \ +z[14] = x[2] * y[12] + x[6] * y[13] + x[10] * y[14] + x[14] * y[15]; \ +z[15] = x[3] * y[12] + x[7] * y[13] + x[11] * y[14] + x[15] * y[15]; + +#define MULTMV(m, v) { \ +float v0 = m[0]*v[0] + m[4]*v[1] + m[8]*v[2] + m[12]*v[3]; \ +float v1 = m[1]*v[0] + m[5]*v[1] + m[9]*v[2] + m[13]*v[3]; \ +float v2 = m[2]*v[0] + m[6]*v[1] + m[10]*v[2] + m[14]*v[3]; \ +float v3 = m[3]*v[0] + m[7]*v[1] + m[11]*v[2] + m[15]*v[3]; \ +v[0] = v0; v[1] = v1; v[2] = v2; v[3] = v3; } + +#define DIVV(v) \ +v[0] /= v[3]; \ +v[1] /= v[3]; \ +v[2] /= v[3]; \ +v[3] /= v[3]; + static CompMetadata cubeMetadata; static int cubeDisplayPrivateIndex; @@ -812,6 +843,7 @@ cubePaintOutput (CompScreen *s, } cs->srcOutput = (output->id != ~0) ? output->id : 0; + cs->paintOrder = BTF; // Always use BTF painting on non-transformed screen. UNWRAP (cs, s, paintOutput); status = (*s->paintOutput) (s, sAttrib, transform, region, output, mask); @@ -833,17 +865,79 @@ cubeDonePaintScreen (CompScreen *s) WRAP (cs, s, donePaintScreen, cubeDonePaintScreen); } +static Bool +cubeCheckFTB (CompScreen *s, + const ScreenPaintAttrib *sAttrib, + const CompTransform *transform, + CompOutput *outputPtr) +{ + float mvp[16]; + CompTransform sTransform = *transform; + + (*s->applyScreenTransform) (s, sAttrib, outputPtr, &sTransform); + transformToScreenSpace (s, outputPtr, -sAttrib->zTranslate, &sTransform); + + MULTM(s->projection, sTransform.m, mvp); + + float pntA[4] = { outputPtr->region.extents.x1, + outputPtr->region.extents.y1, + 0, 1}; + + float pntB[4] = { outputPtr->region.extents.x2, + outputPtr->region.extents.y1, + 0, 1}; + + float pntC[4] = { outputPtr->region.extents.x1 + outputPtr->width / 2.0f, + outputPtr->region.extents.y1 + outputPtr->height / 2.0f, + 0, 1}; + + MULTMV(mvp, pntA); + DIVV(pntA); + + MULTMV(mvp, pntB); + DIVV(pntB); + + MULTMV(mvp, pntC); + DIVV(pntC); + + float vecA[3] = { pntC[0] - pntA[0], + pntC[1] - pntA[1], + pntC[2] - pntA[2]}; + + float vecB[3] = { pntC[0] - pntB[0], + pntC[1] - pntB[1], + pntC[2] - pntB[2]}; + + float ortho[3] = { vecA[1] * vecB[2] - vecA[2] * vecB[1], + vecA[2] * vecB[0] - vecA[0] * vecB[2], + vecA[0] * vecB[1] - vecA[1] * vecB[0]}; + + if (ortho[2] > 0.0f) //The viewport is reversed, should be painted front to back. + return TRUE; + + return FALSE; +} + static void cubeMoveViewportAndPaint (CompScreen *s, const ScreenPaintAttrib *sAttrib, const CompTransform *transform, CompOutput *outputPtr, unsigned int mask, + PaintOrder paintOrder, int dx) { + CUBE_SCREEN (s); + + Bool ftb = cubeCheckFTB(s, sAttrib, transform, outputPtr); + + if ((paintOrder == FTB && !ftb) || + (paintOrder == BTF && ftb)) + return; + int output = (outputPtr->id != ~0) ? outputPtr->id : 0; - CUBE_SCREEN (s); + cs->paintOrder = paintOrder; if (cs->nOutput > 1) { @@ -885,6 +979,103 @@ cubeMoveViewportAndPaint (CompScreen *s, } static void +cubePaintAllViewports (CompScreen *s, + ScreenPaintAttrib *sAttrib, + const CompTransform *transform, + Region region, + CompOutput *outputPtr, + unsigned int mask, + int xMove, + float size, + int hsize, + PaintOrder paintOrder) +{ + CUBE_SCREEN(s); + + ScreenPaintAttrib sa = *sAttrib; + + int i; + int xMoveAdd; + int origXMoveAdd = 0; // dx for the viewport we start painting with (back-most). + int iFirstSign; // 1 if we do xMove += i first and -1 if we do xMove -= i first. + + if (cs->invert == 1) + { + // xMove ==> dx for the viewport which is the nearest to the viewer in z axis. + // xMove +/- hsize / 2 ==> dx for the viewport which is the farest to the viewer in z axis. + + if ((sa.xRotate < 0.0f && hsize % 2 == 1) || + (sa.xRotate > 0.0f && hsize % 2 == 0)) + { + origXMoveAdd = hsize / 2; + iFirstSign = 1; + } + + else + { + origXMoveAdd = -hsize / 2; + iFirstSign = -1; + } + } + + else + { + // xMove is already the dx for farest viewport. + + if (sa.xRotate > 0.0f) + iFirstSign = -1; + else + iFirstSign = 1; + } + + for (i = 0; i <= hsize / 2; i++) + { + // move to the correct viewport (back to front). + xMoveAdd = origXMoveAdd; // move to farest viewport. + xMoveAdd += iFirstSign * i; // move i more viewports to the right / left. + + // needed especially for unfold. + // we paint the viewports around xMove viewport. adding or subtracting hsize from xMove has no effect on + // what viewport we paint, but can make shorter paths. + if (xMoveAdd < -hsize / 2) + xMoveAdd += hsize; + else if (xMoveAdd > hsize / 2) + xMoveAdd -= hsize; + + // paint the viewport. + xMove += xMoveAdd; + + sa.yRotate -= cs->invert * xMoveAdd * 360.0f / size; + cubeMoveViewportAndPaint (s, &sa, transform, outputPtr, mask, + paintOrder, xMove); + sa.yRotate += cs->invert * xMoveAdd * 360.0f / size; + + xMove -= xMoveAdd; + + // do the same for an equally far viewport. + if (i == 0 || i * 2 == hsize) // same viewport. + continue; + + xMoveAdd = origXMoveAdd; // move to farest viewport. + xMoveAdd -= iFirstSign * i; // move i more viewports to the left / right (opposite side from the one chose first) + + if (xMoveAdd < -hsize / 2) + xMoveAdd += hsize; + else if (xMoveAdd > hsize / 2) + xMoveAdd -= hsize; + + xMove += xMoveAdd; + + sa.yRotate -= cs->invert * xMoveAdd * 360.0f / size; + cubeMoveViewportAndPaint (s, &sa, transform, outputPtr, mask, + paintOrder, xMove); + sa.yRotate += cs->invert * xMoveAdd * 360.0f / size; + + xMove -= xMoveAdd; + } +} + +static void cubeGetRotation (CompScreen *s, float *x, float *v) @@ -956,26 +1147,35 @@ cubePaintTopBottom (CompScreen *s, glVertexPointer (3, GL_FLOAT, 0, cs->vertices); - glNormal3f (0.0f, -1.0f, 0.0f); - - if (cs->invert == 1 && size == 4 && cs->texture.name) + int i; + for (i = 0; i < 2; i++) { - enableTexture (s, &cs->texture, COMP_TEXTURE_FILTER_GOOD); - glTexCoordPointer (2, GL_FLOAT, 0, cs->tc); - glDrawArrays (GL_TRIANGLE_FAN, 0, cs->nvertices >> 1); - disableTexture (s, &cs->texture); - glDisableClientState (GL_TEXTURE_COORD_ARRAY); - } - else - { - glDisableClientState (GL_TEXTURE_COORD_ARRAY); - glDrawArrays (GL_TRIANGLE_FAN, 0, cs->nvertices >> 1); + if ((i == 0 && sAttrib->vRotate <= 0.0f) || + (i == 1 && sAttrib->vRotate > 0.0f)) + { + glNormal3f (0.0f, -1.0f, 0.0f); + if (cs->invert == 1 && size == 4 && cs->texture.name) + { + enableTexture (s, &cs->texture, COMP_TEXTURE_FILTER_GOOD); + glTexCoordPointer (2, GL_FLOAT, 0, cs->tc); + glDrawArrays (GL_TRIANGLE_FAN, 0, cs->nvertices >> 1); + disableTexture (s, &cs->texture); + glDisableClientState (GL_TEXTURE_COORD_ARRAY); + } + else + { + glDisableClientState (GL_TEXTURE_COORD_ARRAY); + glDrawArrays (GL_TRIANGLE_FAN, 0, cs->nvertices >> 1); + } + } + else + { + glNormal3f (0.0f, 1.0f, 0.0f); + glDrawArrays (GL_TRIANGLE_FAN, cs->nvertices >> 1, + cs->nvertices >> 1); + } } - glNormal3f (0.0f, 1.0f, 0.0f); - - glDrawArrays (GL_TRIANGLE_FAN, cs->nvertices >> 1, cs->nvertices >> 1); - glNormal3f (0.0f, 0.0f, -1.0f); glPopMatrix (); @@ -996,6 +1196,8 @@ cubePaintTransformedOutput (CompScreen *s, float xRotate, vRotate; int hsize, xMove = 0; float size; + GLenum filter = s->display->textureFilter; + PaintOrder paintOrder; Bool clear; int output = 0; @@ -1047,9 +1249,6 @@ cubePaintTransformedOutput (CompScreen *s, UNWRAP (cs, s, paintTransformedOutput); - sa.xTranslate = sAttrib->xTranslate; - sa.yTranslate = sAttrib->yTranslate; - if (cs->grabIndex) { sa.vRotate = 0.0f; @@ -1063,22 +1262,6 @@ cubePaintTransformedOutput (CompScreen *s, /* distance we move the camera back when unfolding the cube. currently hardcoded to 1.5 but it should probably be optional. */ sa.zCamera -= cs->unfold * 1.5f; - - sa.xRotate = xRotate * cs->invert; - if (sa.xRotate > 0.0f) - { - cs->xrotations = (int) (hsize * sa.xRotate) / 360; - sa.xRotate = sa.xRotate - (360.0f * cs->xrotations) / hsize; - } - else - { - cs->xrotations = (int) (hsize * sa.xRotate) / 360; - sa.xRotate = sa.xRotate - - (360.0f * cs->xrotations) / hsize + 360.0f / hsize; - cs->xrotations--; - } - - sa.xRotate = sa.xRotate / size * hsize; } else { @@ -1090,131 +1273,46 @@ cubePaintTransformedOutput (CompScreen *s, sa.vRotate = vRotate; sa.zTranslate = -cs->invert * cs->distance; - sa.xRotate = xRotate * cs->invert; - if (sa.xRotate > 0.0f) - { - cs->xrotations = (int) (size * sa.xRotate) / 360; - sa.xRotate = sa.xRotate - (360.0f * cs->xrotations) / size; - } - else - { - cs->xrotations = (int) (size * sa.xRotate) / 360; - sa.xRotate = sa.xRotate - - (360.0f * cs->xrotations) / size + 360.0f / size; - cs->xrotations--; - } - } - - if (!clear && cs->grabIndex == 0 && hsize > 2 && - (cs->invert != 1 || sa.vRotate != 0.0f || sa.yTranslate != 0.0f)) - { - (*cs->paintTopBottom) (s, &sa, transform, outputPtr, hsize); } - /* outside cube */ - if (cs->invert == 1) - { - if (cs->grabIndex || hsize > 4) - { - GLenum filter; - int i; - - xMove = cs->xrotations - ((hsize >> 1) - 1); - sa.yRotate += (360.0f / size) * ((hsize >> 1) - 1); - - filter = s->display->textureFilter; - if (cs->grabIndex && cs->opt[CUBE_SCREEN_OPTION_MIPMAP].value.b) - s->display->textureFilter = GL_LINEAR_MIPMAP_LINEAR; - - for (i = 0; i < hsize; i++) - { - cubeMoveViewportAndPaint (s, &sa, transform, outputPtr, mask, - xMove); - - sa.yRotate -= 360.0f / size; - xMove++; - } - - s->display->textureFilter = filter; - } - else - { - if (xRotate != 0.0f) - { - xMove = cs->xrotations; - - cubeMoveViewportAndPaint (s, &sa, transform, outputPtr, mask, - xMove); - - xMove++; - } - - sa.yRotate -= 360.0f / size; - - cubeMoveViewportAndPaint (s, &sa, transform, outputPtr, mask, - xMove); - } - } + if (sa.xRotate > 0.0f) + cs->xrotations = (int) (hsize * sa.xRotate + 180) / 360; else - { - if (sa.xRotate > 180.0f / size) - { - sa.yRotate -= 360.0f / size; - cs->xrotations++; - } + cs->xrotations = (int) (hsize * sa.xRotate - 180) / 360; - sa.yRotate -= 360.0f / size; - xMove = -1 - cs->xrotations; + sa.xRotate -= (360.0f * cs->xrotations) / hsize; + sa.xRotate *= cs->invert; - if (cs->grabIndex) - { - GLenum filter; - int i; + sa.xRotate = sa.xRotate / size * hsize; - filter = s->display->textureFilter; - if (cs->opt[CUBE_SCREEN_OPTION_MIPMAP].value.b) - s->display->textureFilter = GL_LINEAR_MIPMAP_LINEAR; + xMove = cs->xrotations; - if (sa.xRotate > 180.0f / size) - { - xMove -= ((hsize >> 1) - 2); - sa.yRotate -= (360.0f / size) * ((hsize >> 1) - 2); - } - else - { - xMove -= ((hsize >> 1) - 1); - sa.yRotate -= (360.0f / size) * ((hsize >> 1) - 1); - } + if (cs->grabIndex && cs->opt[CUBE_SCREEN_OPTION_MIPMAP].value.b) + s->display->textureFilter = GL_LINEAR_MIPMAP_LINEAR; - for (i = 0; i < hsize; i++) - { - cubeMoveViewportAndPaint (s, &sa, transform, outputPtr, mask, - xMove); + if (cs->invert == 1) + paintOrder = FTB; // Outside cube - start with FTB faces. + else + paintOrder = BTF; // Inside cube - start with BTF faces. - sa.yRotate += 360.0f / size; - xMove++; - } + if (cs->invert == -1) + cubePaintAllViewports(s, &sa, transform, region, outputPtr, mask, xMove, size, hsize, paintOrder); - s->display->textureFilter = filter; - } - else - { - cubeMoveViewportAndPaint (s, &sa, transform, outputPtr, mask, - xMove); - - sa.yRotate += 360.0f / size; - xMove = -cs->xrotations; + if (!clear && cs->grabIndex == 0 && hsize > 2 && + (cs->invert != 1 || sa.vRotate != 0.0f || sa.yTranslate != 0.0f)) + { + (*cs->paintTopBottom) (s, &sa, transform, outputPtr, hsize); + } - cubeMoveViewportAndPaint (s, &sa, transform, outputPtr, mask, - xMove); + if (cs->invert == 1) + paintOrder = BTF; // Outside cube - continue with BTF faces. + else + paintOrder = FTB; // Inside cube - continue with FTB faces. - sa.yRotate += 360.0f / size; - xMove = 1 - cs->xrotations; + if (cs->invert == 1) + cubePaintAllViewports(s, &sa, transform, region, outputPtr, mask, xMove, size, hsize, paintOrder); - cubeMoveViewportAndPaint (s, &sa, transform, outputPtr, mask, - xMove); - } - } + s->display->textureFilter = filter; WRAP (cs, s, paintTransformedOutput, cubePaintTransformedOutput); } @@ -1320,6 +1418,27 @@ cubePaintBackground (CompScreen *s, } static void +cubeInitWindowWalker (CompScreen *s, CompWalker* walker) +{ + CUBE_SCREEN (s); + + UNWRAP (cs, s, initWindowWalker); + (*s->initWindowWalker) (s, walker); + WRAP (cs, s, initWindowWalker, cubeInitWindowWalker); + + if (cs->paintOrder == FTB) + { + WalkInitProc tmpInit = walker->first; + walker->first = walker->last; + walker->last = tmpInit; + + WalkStepProc tmpStep = walker->next; + walker->next = walker->prev; + walker->prev = tmpStep; + } +} + +static void cubeApplyScreenTransform (CompScreen *s, const ScreenPaintAttrib *sAttrib, CompOutput *output, @@ -1713,6 +1832,7 @@ cubeInitScreen (CompPlugin *p, WRAP (cs, s, applyScreenTransform, cubeApplyScreenTransform); WRAP (cs, s, setScreenOption, cubeSetGlobalScreenOption); WRAP (cs, s, outputChangeNotify, cubeOutputChangeNotify); + WRAP (cs, s, initWindowWalker, cubeInitWindowWalker); return TRUE; } @@ -1734,6 +1854,7 @@ cubeFiniScreen (CompPlugin *p, UNWRAP (cs, s, applyScreenTransform); UNWRAP (cs, s, setScreenOption); UNWRAP (cs, s, outputChangeNotify); + UNWRAP (cs, s, initWindowWalker); finiTexture (s, &cs->texture); finiTexture (s, &cs->sky); -- 1.4.4.2
From 33a0603d8d1abc0074c98de6d6d74d3e1851a0af Mon Sep 17 00:00:00 2001 From: Roi Cohen <[EMAIL PROTECTED](none)> Date: Tue, 5 Jun 2007 14:49:33 +0300 Subject: [PATCH] plugin events --- include/cube.h | 15 ++++++++- plugins/cube.c | 95 ++++++++++++++++++++++++++++++++++++++++++++++++++++-- plugins/rotate.c | 29 ++++++++++++++++ 3 files changed, 135 insertions(+), 4 deletions(-) diff --git a/include/cube.h b/include/cube.h index bc44a32..0dcb14b 100644 --- a/include/cube.h +++ b/include/cube.h @@ -25,7 +25,7 @@ #include <compiz.h> -#define CUBE_ABIVERSION 20070604 +#define CUBE_ABIVERSION 20070605 #define CUBE_DISPLAY_OPTION_ABI 0 #define CUBE_DISPLAY_OPTION_INDEX 1 @@ -38,6 +38,8 @@ typedef struct _CubeDisplay { int screenPrivateIndex; CompOption opt[CUBE_DISPLAY_OPTION_NUM]; + + HandleCompizEventProc handleCompizEvent; } CubeDisplay; #define CUBE_SCREEN_OPTION_COLOR 0 @@ -77,6 +79,13 @@ typedef enum _PaintOrder FTB } PaintOrder; +typedef enum _RotationMode +{ + NoRotation = 0, + RotationChange, + RotationManual +} RotationMode; + typedef struct _CubeScreen { PreparePaintScreenProc preparePaintScreen; DonePaintScreenProc donePaintScreen; @@ -131,6 +140,10 @@ typedef struct _CubeScreen { float outputXOffset; float outputYOffset; + RotationMode rotationMode; + Bool disableCaps; + Bool paintAllViewports; + CompTexture *bg; int nBg; } CubeScreen; diff --git a/plugins/cube.c b/plugins/cube.c index f28b9f5..43c6578 100644 --- a/plugins/cube.c +++ b/plugins/cube.c @@ -1295,10 +1295,10 @@ cubePaintTransformedOutput (CompScreen *s, else paintOrder = BTF; // Inside cube - start with BTF faces. - if (cs->invert == -1) + if (cs->invert == -1 || cs->paintAllViewports) cubePaintAllViewports(s, &sa, transform, region, outputPtr, mask, xMove, size, hsize, paintOrder); - if (!clear && cs->grabIndex == 0 && hsize > 2 && + if (!clear && cs->grabIndex == 0 && hsize > 2 && !cs->disableCaps && (cs->invert != 1 || sa.vRotate != 0.0f || sa.yTranslate != 0.0f)) { (*cs->paintTopBottom) (s, &sa, transform, outputPtr, hsize); @@ -1309,7 +1309,7 @@ cubePaintTransformedOutput (CompScreen *s, else paintOrder = FTB; // Inside cube - continue with FTB faces. - if (cs->invert == 1) + if (cs->invert == 1 || cs->paintAllViewports) cubePaintAllViewports(s, &sa, transform, region, outputPtr, mask, xMove, size, hsize, paintOrder); s->display->textureFilter = filter; @@ -1458,6 +1458,85 @@ cubeApplyScreenTransform (CompScreen *s, matrixTranslate (transform, -cs->outputXOffset, cs->outputYOffset, 0.0f); } +static void cubeHandleCompizEvent(CompDisplay * d, char *pluginName, + char *eventName, CompOption * option, int nOption) +{ + CUBE_DISPLAY(d); + + UNWRAP (cd, d, handleCompizEvent); + (*d->handleCompizEvent) (d, pluginName, eventName, option, nOption); + WRAP (cd, d, handleCompizEvent, cubeHandleCompizEvent); + + if (strcmp(pluginName, "3d") == 0) + { + if (strcmp(eventName, "disableCapsEvent") == 0) + { + Window xid = getIntOptionNamed(option, nOption, "root", 0); + CompScreen *s = findScreenAtDisplay(d, xid); + + if (s) + { + CUBE_SCREEN(s); + cs->disableCaps = getBoolOptionNamed(option, nOption, "disableCaps", FALSE); + } + } + + else if (strcmp(eventName, "paintAllViewportsEvent") == 0) + { + Window xid = getIntOptionNamed(option, nOption, "root", 0); + CompScreen *s = findScreenAtDisplay(d, xid); + + if (s) + { + CUBE_SCREEN(s); + cs->paintAllViewports = getBoolOptionNamed(option, nOption, "paintAllViewports", FALSE); + } + } + } + if (strcmp(pluginName, "rotate") == 0) + { + if (strcmp(eventName, "rotateEvent") == 0) + { + Window xid = getIntOptionNamed(option, nOption, "root", 0); + CompScreen *s = findScreenAtDisplay(d, xid); + + if (s) + { + CUBE_SCREEN(s); + Bool rotate = getBoolOptionNamed(option, nOption, "rotating", FALSE); + Bool manual = getBoolOptionNamed(option, nOption, "manual", FALSE); + + if (rotate && manual) + cs->rotationMode = RotationManual; + else if (rotate) + cs->rotationMode = RotationChange; + else + cs->rotationMode = NoRotation; + damageScreen(s); + } + } + } +} + +static void +cubeFoldEvent(CompScreen *s, Bool unfolded) +{ + CompOption o[2]; + + o[0].type = CompOptionTypeInt; + o[0].name = "root"; + o[0].value.i = s->root; + + o[1].type = CompOptionTypeBool; + o[1].name = "unfolded"; + o[1].value.b = unfolded; + + (*s->display->handleCompizEvent) (s->display, + "cube", + "unfoldEvent", + o, 2); +} + static Bool cubeUnfold (CompDisplay *d, CompAction *action, @@ -1487,6 +1566,7 @@ cubeUnfold (CompDisplay *d, if (cs->grabIndex) { cs->unfolded = TRUE; + cubeFoldEvent (s, TRUE); damageScreen (s); } @@ -1522,6 +1602,7 @@ cubeFold (CompDisplay *d, if (cs->grabIndex) { cs->unfolded = FALSE; + cubeFoldEvent (s, FALSE); damageScreen (s); } } @@ -1710,6 +1791,8 @@ cubeInitDisplay (CompPlugin *p, d->privates[cubeDisplayPrivateIndex].ptr = cd; + WRAP (cd, d, handleCompizEvent, cubeHandleCompizEvent); + return TRUE; } @@ -1721,6 +1804,8 @@ cubeFiniDisplay (CompPlugin *p, freeScreenPrivateIndex (d, cd->screenPrivateIndex); + UNWRAP (cd, d, handleCompizEvent); + compFiniDisplayOptions (d, cd->opt, CUBE_DISPLAY_OPTION_NUM); free (cd); @@ -1807,6 +1892,10 @@ cubeInitScreen (CompPlugin *p, cs->bg = NULL; cs->nBg = 0; + cs->disableCaps = FALSE; + cs->paintAllViewports = FALSE; + cs->rotationMode = NoRotation; + memset (cs->cleared, 0, sizeof (cs->cleared)); cubeUpdateOutputs (s); diff --git a/plugins/rotate.c b/plugins/rotate.c index b91d387..4e44465 100644 --- a/plugins/rotate.c +++ b/plugins/rotate.c @@ -255,6 +255,30 @@ rotateReleaseMoveWindow (CompScreen *s) rs->moveWindow = None; } +static void rotateEvent(CompScreen *s, + Bool rotating, + Bool manual) +{ + CompOption o[3]; + + o[0].type = CompOptionTypeInt; + o[0].name = "root"; + o[0].value.i = s->root; + + o[1].type = CompOptionTypeBool; + o[1].name = "rotating"; + o[1].value.b = rotating; + + o[2].type = CompOptionTypeBool; + o[2].name = "manual"; + o[2].value.b = manual; + + (*s->display->handleCompizEvent)(s->display, + "rotate", + "rotateEvent", + o, 3); +} + static void rotatePreparePaintScreen (CompScreen *s, int msSinceLastPaint) @@ -342,6 +366,7 @@ rotatePreparePaintScreen (CompScreen *s, else tx = (s->hsize * xrot / 360.0f) + 0.5f; + rotateEvent (s, FALSE, FALSE); moveScreenViewport (s, tx, 0, TRUE); rs->xrot = 0.0f; @@ -500,6 +525,10 @@ rotateInitiate (CompDisplay *d, rs->moving = FALSE; rs->slow = FALSE; + /* notify other plugins that rotation starts - if action is + non-NULL, we are called from the 'Initiate rotate' binding */ + rotateEvent (s, TRUE, (action != NULL)); + if (!rs->grabIndex) { rs->grabIndex = pushScreenGrab (s, s->invisibleCursor, "rotate"); -- 1.4.4.2
From 969ff01695db71f7d2030cf61b2aa1d47a83301a Mon Sep 17 00:00:00 2001 From: Roi Cohen <[EMAIL PROTECTED](none)> Date: Tue, 5 Jun 2007 15:32:02 +0300 Subject: [PATCH] transparent cube --- include/cube.h | 42 ++++++++------ metadata/cube.xml.in | 29 +++++++++ plugins/cube.c | 156 +++++++++++++++++++++++++++++++++++++++++++++++--- 3 files changed, 202 insertions(+), 25 deletions(-) diff --git a/include/cube.h b/include/cube.h index 0dcb14b..520cf3d 100644 --- a/include/cube.h +++ b/include/cube.h @@ -25,7 +25,7 @@ #include <compiz.h> -#define CUBE_ABIVERSION 20070605 +#define CUBE_ABIVERSION 20070606 #define CUBE_DISPLAY_OPTION_ABI 0 #define CUBE_DISPLAY_OPTION_INDEX 1 @@ -42,22 +42,26 @@ typedef struct _CubeDisplay { HandleCompizEventProc handleCompizEvent; } CubeDisplay; -#define CUBE_SCREEN_OPTION_COLOR 0 -#define CUBE_SCREEN_OPTION_IN 1 -#define CUBE_SCREEN_OPTION_SCALE_IMAGE 2 -#define CUBE_SCREEN_OPTION_IMAGES 3 -#define CUBE_SCREEN_OPTION_SKYDOME 4 -#define CUBE_SCREEN_OPTION_SKYDOME_IMG 5 -#define CUBE_SCREEN_OPTION_SKYDOME_ANIM 6 -#define CUBE_SCREEN_OPTION_SKYDOME_GRAD_START 7 -#define CUBE_SCREEN_OPTION_SKYDOME_GRAD_END 8 -#define CUBE_SCREEN_OPTION_ACCELERATION 9 -#define CUBE_SCREEN_OPTION_SPEED 10 -#define CUBE_SCREEN_OPTION_TIMESTEP 11 -#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_COLOR 0 +#define CUBE_SCREEN_OPTION_IN 1 +#define CUBE_SCREEN_OPTION_SCALE_IMAGE 2 +#define CUBE_SCREEN_OPTION_IMAGES 3 +#define CUBE_SCREEN_OPTION_SKYDOME 4 +#define CUBE_SCREEN_OPTION_SKYDOME_IMG 5 +#define CUBE_SCREEN_OPTION_SKYDOME_ANIM 6 +#define CUBE_SCREEN_OPTION_SKYDOME_GRAD_START 7 +#define CUBE_SCREEN_OPTION_SKYDOME_GRAD_END 8 +#define CUBE_SCREEN_OPTION_ACCELERATION 9 +#define CUBE_SCREEN_OPTION_SPEED 10 +#define CUBE_SCREEN_OPTION_TIMESTEP 11 +#define CUBE_SCREEN_OPTION_MIPMAP 12 +#define CUBE_SCREEN_OPTION_BACKGROUNDS 13 +#define CUBE_SCREEN_OPTION_ADJUST_IMAGE 14 +#define CUBE_SCREEN_OPTION_ACTIVE_OPACITY 15 +#define CUBE_SCREEN_OPTION_INACTIVE_OPACITY 16 +#define CUBE_SCREEN_OPTION_FADE_TIME 17 +#define CUBE_SCREEN_OPTION_TRANSPARENT_MANUAL_ONLY 18 +#define CUBE_SCREEN_OPTION_NUM 19 typedef void (*CubeGetRotationProc) (CompScreen *s, float *x, @@ -92,6 +96,7 @@ typedef struct _CubeScreen { PaintOutputProc paintOutput; PaintTransformedOutputProc paintTransformedOutput; PaintBackgroundProc paintBackground; + PaintWindowProc paintWindow; ApplyScreenTransformProc applyScreenTransform; SetScreenOptionProc setScreenOption; OutputChangeNotifyProc outputChangeNotify; @@ -144,6 +149,9 @@ typedef struct _CubeScreen { Bool disableCaps; Bool paintAllViewports; + float desktopOpacity; + float toOpacity; + CompTexture *bg; int nBg; } CubeScreen; diff --git a/metadata/cube.xml.in b/metadata/cube.xml.in index 0f674e7..7405531 100644 --- a/metadata/cube.xml.in +++ b/metadata/cube.xml.in @@ -134,6 +134,35 @@ <_long>Adjust top face image to rotation</_long> <default>false</default> </option> + <option name="active_opacity" type="float"> + <_short>Opacity During Rotation</_short> + <_long>Opacity of desktop window during rotation.</_long> + <default>30.0</default> + <min>0.0</min> + <max>100.0</max> + <precision>1.0</precision> + </option> + <option name="inactive_opacity" type="float"> + <_short>Opacity When Not Rotating</_short> + <_long>Opacity of desktop window when not rotating.</_long> + <default>100.0</default> + <min>0.0</min> + <max>100.0</max> + <precision>1.0</precision> + </option> + <option name="fade_time" type="float"> + <_short>Fade Time</_short> + <_long>Desktop Window Opacity Fade Time.</_long> + <default>1.0</default> + <min>0.0</min> + <max>10.0</max> + <precision>0.1</precision> + </option> + <option name="transparent_manual_only" type="bool"> + <_short>Transparency Only on Mouse Rotate</_short> + <_long>Initiates Cube transparency only if rotation is mouse driven.</_long> + <default>true</default> + </option> </screen> </plugin> </compiz> diff --git a/plugins/cube.c b/plugins/cube.c index 43c6578..1963b66 100644 --- a/plugins/cube.c +++ b/plugins/cube.c @@ -818,10 +818,42 @@ cubePreparePaintScreen (CompScreen *s, memset (cs->cleared, 0, sizeof (Bool) * s->nOutputDev); + //transparency, mostly copied/ported from beryl's cube.c, orig. by onestone + if (cs->rotationMode != NoRotation && ((cs->rotationMode == RotationManual) || + !(cs->opt[CUBE_SCREEN_OPTION_TRANSPARENT_MANUAL_ONLY].value.b))) + { + cs->toOpacity = + (cs->opt[CUBE_SCREEN_OPTION_ACTIVE_OPACITY].value.f / 100.0f) * OPAQUE; + } + else + cs->toOpacity = + (cs->opt[CUBE_SCREEN_OPTION_INACTIVE_OPACITY].value.f / 100.0f) * OPAQUE; + + if (cs->opt[CUBE_SCREEN_OPTION_FADE_TIME].value.f == 0.0f) + cs->desktopOpacity = cs->toOpacity; + + else if (cs->desktopOpacity != cs->toOpacity) + { + float steps = (msSinceLastPaint * OPAQUE / 1000.0) / + cs->opt[CUBE_SCREEN_OPTION_FADE_TIME].value.f; + if (steps < 12) + steps = 12; + + if (cs->toOpacity > cs->desktopOpacity) + { + cs->desktopOpacity += steps; + cs->desktopOpacity = MIN(cs->toOpacity, cs->desktopOpacity); + } + if (cs->toOpacity < cs->desktopOpacity) + { + cs->desktopOpacity -= steps; + cs->desktopOpacity = MAX(cs->toOpacity, cs->desktopOpacity); + } + } + UNWRAP (cs, s, preparePaintScreen); (*s->preparePaintScreen) (s, msSinceLastPaint); WRAP (cs, s, preparePaintScreen, cubePreparePaintScreen); - } static Bool @@ -836,7 +868,7 @@ cubePaintOutput (CompScreen *s, CUBE_SCREEN (s); - if (cs->grabIndex) + if (cs->grabIndex || cs->desktopOpacity != OPAQUE) { mask &= ~PAINT_SCREEN_REGION_MASK; mask |= PAINT_SCREEN_TRANSFORMED_MASK; @@ -857,7 +889,7 @@ cubeDonePaintScreen (CompScreen *s) { CUBE_SCREEN (s); - if (cs->grabIndex) + if (cs->grabIndex || cs->desktopOpacity != cs->toOpacity) damageScreen (s); UNWRAP (cs, s, donePaintScreen); @@ -1131,7 +1163,7 @@ cubePaintTopBottom (CompScreen *s, screenLighting (s, TRUE); - glColor3usv (cs->color); + glColor4us (cs->color[0], cs->color[1], cs->color[2], cs->desktopOpacity); glPushMatrix (); @@ -1145,6 +1177,13 @@ cubePaintTopBottom (CompScreen *s, glTranslatef (cs->outputXOffset, -cs->outputYOffset, 0.0f); glScalef (cs->outputXScale, cs->outputYScale, 1.0f); + if (cs->desktopOpacity != OPAQUE) + { + screenTexEnvMode (s, GL_MODULATE); + glEnable(GL_BLEND); + glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); + } + glVertexPointer (3, GL_FLOAT, 0, cs->vertices); int i; @@ -1182,6 +1221,10 @@ cubePaintTopBottom (CompScreen *s, glColor4usv (defaultColor); glEnableClientState (GL_TEXTURE_COORD_ARRAY); + + screenTexEnvMode(s, GL_REPLACE); + glDisable(GL_BLEND); + glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA); } static void @@ -1199,6 +1242,7 @@ cubePaintTransformedOutput (CompScreen *s, GLenum filter = s->display->textureFilter; PaintOrder paintOrder; Bool clear; + Bool wasCulled = FALSE; int output = 0; CUBE_SCREEN (s); @@ -1208,6 +1252,13 @@ cubePaintTransformedOutput (CompScreen *s, hsize = s->hsize * cs->nOutput; size = hsize; + if (cs->desktopOpacity != OPAQUE) + { + wasCulled = glIsEnabled(GL_CULL_FACE); + if (wasCulled) + glDisable(GL_CULL_FACE); + } + if (!cs->fullscreenOutput) { cs->outputXScale = (float) s->width / s->outputDev[output].width; @@ -1295,11 +1346,11 @@ cubePaintTransformedOutput (CompScreen *s, else paintOrder = BTF; // Inside cube - start with BTF faces. - if (cs->invert == -1 || cs->paintAllViewports) + if (cs->invert == -1 || cs->paintAllViewports || cs->desktopOpacity != OPAQUE) cubePaintAllViewports(s, &sa, transform, region, outputPtr, mask, xMove, size, hsize, paintOrder); if (!clear && cs->grabIndex == 0 && hsize > 2 && !cs->disableCaps && - (cs->invert != 1 || sa.vRotate != 0.0f || sa.yTranslate != 0.0f)) + (cs->invert != 1 || sa.vRotate != 0.0f || sa.yTranslate != 0.0f || cs->desktopOpacity != OPAQUE)) { (*cs->paintTopBottom) (s, &sa, transform, outputPtr, hsize); } @@ -1309,15 +1360,62 @@ cubePaintTransformedOutput (CompScreen *s, else paintOrder = FTB; // Inside cube - continue with FTB faces. - if (cs->invert == 1 || cs->paintAllViewports) + if (cs->invert == 1 || cs->paintAllViewports || cs->desktopOpacity != OPAQUE) cubePaintAllViewports(s, &sa, transform, region, outputPtr, mask, xMove, size, hsize, paintOrder); s->display->textureFilter = filter; + if (cs->desktopOpacity != OPAQUE && wasCulled) + glEnable(GL_CULL_FACE); + WRAP (cs, s, paintTransformedOutput, cubePaintTransformedOutput); } static void +cubeSetBackgroundOpacity(CompScreen* s) +{ + CUBE_SCREEN(s); + + if (cs->desktopOpacity != OPAQUE) + { + if (s->desktopWindowCount) + { + glColor4us(0, 0, 0, 0); + glEnable(GL_BLEND); + } + else + { + glColor4us(0xffff, 0xffff, 0xffff, cs->desktopOpacity); + glEnable(GL_BLEND); + glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); + glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); + } + } +} + +static void +cubeUnSetBackgroundOpacity(CompScreen* s) +{ + CUBE_SCREEN(s); + + if (cs->desktopOpacity != OPAQUE) + { + if (s->desktopWindowCount) + { + glColor3usv(defaultColor); + glDisable(GL_BLEND); + } + else + { + glColor3usv(defaultColor); + glDisable(GL_BLEND); + glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA); + screenTexEnvMode(s, GL_REPLACE); + } + } +} + +static void cubePaintBackground (CompScreen *s, Region region, unsigned int mask) @@ -1326,6 +1424,8 @@ cubePaintBackground (CompScreen *s, CUBE_SCREEN (s); + cubeSetBackgroundOpacity(s); + n = cs->opt[CUBE_SCREEN_OPTION_BACKGROUNDS].value.list.nValue; if (n) { @@ -1336,13 +1436,17 @@ cubePaintBackground (CompScreen *s, GLfloat *d, *data; if (!nBox) + { + cubeUnSetBackgroundOpacity(s); return; + } n = (s->x * cs->nOutput + cs->srcOutput) % n; if (s->desktopWindowCount) { cubeUnloadBackgrounds (s); + cubeUnSetBackgroundOpacity(s); return; } else @@ -1358,7 +1462,10 @@ cubePaintBackground (CompScreen *s, data = malloc (sizeof (GLfloat) * nBox * 16); if (!data) + { + cubeUnSetBackgroundOpacity(s); return; + } d = data; n = nBox; @@ -1415,6 +1522,31 @@ cubePaintBackground (CompScreen *s, (*s->paintBackground) (s, region, mask); WRAP (cs, s, paintBackground, cubePaintBackground); } + + cubeUnSetBackgroundOpacity(s); +} + +static Bool +cubePaintWindow (CompWindow *w, + const WindowPaintAttrib *attrib, + const CompTransform *transform, + Region region, + unsigned int mask) +{ + Bool status; + CompScreen* s = w->screen; + CUBE_SCREEN(s); + + WindowPaintAttrib wa = *attrib; + + if (w->type & CompWindowTypeDesktopMask) + wa.opacity = cs->desktopOpacity; + + UNWRAP (cs, s, paintWindow); + status = (*s->paintWindow) (w, &wa, transform, region, mask); + WRAP (cs, s, paintWindow, cubePaintWindow); + + return status; } static void @@ -1826,7 +1958,11 @@ 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 }, + { "active_opacity", "float", "<min>0.0</min><max>100.0</max>", 0, 0 }, + { "inactive_opacity", "float", "<min>0.0</min><max>100.0</max>", 0, 0 }, + { "fade_time", "float", "<min>0.0</min>", 0, 0 }, + { "transparent_manual_only", "bool", 0, 0, 0 } }; static Bool @@ -1896,6 +2032,8 @@ cubeInitScreen (CompPlugin *p, cs->paintAllViewports = FALSE; cs->rotationMode = NoRotation; + cs->desktopOpacity = OPAQUE; + memset (cs->cleared, 0, sizeof (cs->cleared)); cubeUpdateOutputs (s); @@ -1918,6 +2056,7 @@ cubeInitScreen (CompPlugin *p, WRAP (cs, s, paintOutput, cubePaintOutput); WRAP (cs, s, paintTransformedOutput, cubePaintTransformedOutput); WRAP (cs, s, paintBackground, cubePaintBackground); + WRAP (cs, s, paintWindow, cubePaintWindow); WRAP (cs, s, applyScreenTransform, cubeApplyScreenTransform); WRAP (cs, s, setScreenOption, cubeSetGlobalScreenOption); WRAP (cs, s, outputChangeNotify, cubeOutputChangeNotify); @@ -1940,6 +2079,7 @@ cubeFiniScreen (CompPlugin *p, UNWRAP (cs, s, paintOutput); UNWRAP (cs, s, paintTransformedOutput); UNWRAP (cs, s, paintBackground); + UNWRAP (cs, s, paintWindow); UNWRAP (cs, s, applyScreenTransform); UNWRAP (cs, s, setScreenOption); UNWRAP (cs, s, outputChangeNotify); -- 1.4.4.2
_______________________________________________ compiz mailing list compiz@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/compiz