/*
 * After painting clean up
 */
static void
smartputDonePaintScreen (CompScreen *s)
{
    CompWindow *w = NULL;

    SMARTPUT_SCREEN (s);
    if(sps->lastWindow != None)
    {
        w = findWindowAtScreen (s,sps->lastWindow);
    }

    if (sps->animation && sps->grabIndex)
	damageScreen (s);
    else
    {
	if(w)
	{
	    SMARTPUT_WINDOW (w);
	    if(spw->mask && spw->xwc)
	    {
		if (w->mapNum && (spw->mask & (CWWidth | CWHeight)))
		{
		    sendSyncRequest (w);
		    configureXWindow (w, spw->mask, spw->xwc);
		}
		spw->mask = 0;
		free(spw->xwc);
		spw->xwc  = NULL;
	    }
	}
	if (sps->grabIndex)
	{
	    /* release the screen grab */
	    removeScreenGrab (s, sps->grabIndex, NULL);
	    sps->grabIndex = 0;
	}
    }

    UNWRAP (sps, s, donePaintScreen);
    (*s->donePaintScreen) (s);
    WRAP (sps, s, donePaintScreen, smartputDonePaintScreen);
}
示例#2
0
static void
winrulesUpdateWindowSize (CompWindow *w,
                          int        width,
                          int        height)
{
	XWindowChanges xwc;
	unsigned int xwcm = 0;

	if (width != w->serverWidth)
		xwcm |= CWWidth;
	if (height != w->serverHeight)
		xwcm |= CWHeight;

	xwc.width = width;
	xwc.height = height;

	if (w->mapNum && xwcm)
		sendSyncRequest (w);

	configureXWindow (w, xwcm, &xwc);
}
static void FWHandleIPWResizeMotionEvent (CompWindow *w, unsigned int x, unsigned int y)
{
    FREEWINS_WINDOW (w);

    int dx = (x - lastPointerX) * 10;
    int dy = (y - lastPointerY) * 10;

    fww->winH += dx;
    fww->winW += dy;

    /* In order to prevent a window redraw on resize
     * on every motion event we have a threshold
     */

     /* FIXME: cf-love: Instead of actually resizing the window, scale it up, then resize it */

    if (fww->winH - 10 > w->height || fww->winW - 10 > w->width)
    {
        XWindowChanges xwc;
        unsigned int   mask = CWX | CWY | CWWidth | CWHeight;

        xwc.x = w->serverX;
        xwc.y = w->serverX;
        xwc.width = fww->winW;
        xwc.height = fww->winH;

        if (xwc.width == w->serverWidth)
	    mask &= ~CWWidth;

        if (xwc.height == w->serverHeight)
	    mask &= ~CWHeight;

        if (w->mapNum && (mask & (CWWidth | CWHeight)))
	    sendSyncRequest (w);

        configureXWindow (w, mask, &xwc);
    }

}
static Bool
tileSetNewWindowSize (CompWindow *w)
{
    XWindowChanges xwc;
    unsigned int   mask = CWX | CWY | CWWidth | CWHeight;

    TILE_WINDOW (w);
    TILE_SCREEN (w->screen);

    xwc.x = tw->newCoords.x;
    xwc.y = tw->newCoords.y;
    xwc.width = tw->newCoords.width;
    xwc.height = tw->newCoords.height;

    if (ts->tileType == -1)
    {
	if (tw->savedValid)
	    maximizeWindow (w, tw->savedMaxState);
    }
    else
	maximizeWindow (w, 0);

    if (xwc.width == w->serverWidth)
	mask &= ~CWWidth;

    if (xwc.height == w->serverHeight)
	mask &= ~CWHeight;

    if (w->mapNum && (mask & (CWWidth | CWHeight)))
	sendSyncRequest (w);

    configureXWindow (w, mask, &xwc);
    tw->needConfigure = FALSE;

    return TRUE;
}
/*
 * Buggy
 */
static Bool
smartputAllTrigger (CompDisplay     *d,
		    CompAction      *action,
		    CompActionState state,
		    CompOption      *option,
		    int             nOption)
{
    Window     xid;
    CompWindow *w;
    CompScreen *s;
    int grabIndex = 0;

    xid = getIntOptionNamed (option, nOption, "window", 0);
    w   = findWindowAtDisplay (d, xid);
    if (w)
    {
	s = w->screen;

	if(otherScreenGrabExist (s, "smartput", 0))
	    return FALSE;

	/*
	 * Grab the screen
	 */

	grabIndex = pushScreenGrab (s, s->invisibleCursor, "smartput");

	if(!grabIndex)
	    return FALSE;

	CompWindow *window;
	for (window = s->windows; window; window = window->next)
	{
	    if(!smartputSameViewport (window,w) )
	       continue;
	    int            width, height;
	    unsigned int   mask;
	    XWindowChanges xwc;

	    mask = smartputComputeResize (window, &xwc);
	    if (mask)
	    {
		if (constrainNewWindowSize (window, xwc.width, xwc.height,
					    &width, &height))
		{
		    mask |= CWWidth | CWHeight;
		    xwc.width  = width;
		    xwc.height = height;
		}

		if (window->mapNum && (mask & (CWWidth | CWHeight)))
		    sendSyncRequest (window);

		configureXWindow (window, mask, &xwc);
	    }
	}
    }
    if(grabIndex)
	removeScreenGrab (s,grabIndex, NULL);
    return TRUE;
}
static Bool
sessionReadWindow (CompWindow *w)
{
    CompDisplay        *d = w->screen->display;
    XWindowChanges     xwc;
    unsigned int       xwcm = 0;
    char               *title, *role, *clientId, *command;
    SessionWindowList  *cur;

    SESSION_CORE (&core);
    SESSION_DISPLAY (d);

    /* optimization: don't mess around with getting X properties
       if there is nothing to match */
    if (!sc->windowList)
	return FALSE;

    if (!isSessionWindow (w))
	return FALSE;

    clientId = sessionGetClientLeaderProperty (w, sd->clientIdAtom);
    if (!clientId && !sd->opt[SESSION_DISPLAY_OPTION_SAVE_LEGACY].value.b)
	return FALSE;

    command  = sessionGetClientLeaderProperty (w, sd->commandAtom);
    title    = sessionGetWindowTitle (w);
    role     = sessionGetTextProperty (d, w->id, sd->roleAtom);

    for (cur = sc->windowList; cur; cur = cur->next)
    {
	if (clientId && cur->clientId && strcmp (clientId, cur->clientId) == 0)
	{
	    /* try to match role as well if possible (see ICCCM 5.1) */
	    if (role && cur->role)
	    {
		if (strcmp (role, cur->role) == 0)
		    break;
	    }
	    else
	    {
		if (sessionMatchWindowClass (w, cur))
		    break;
	    }
	}
	else if (sd->opt[SESSION_DISPLAY_OPTION_SAVE_LEGACY].value.b)
	{
	    if (cur->command && command && sessionMatchWindowClass (w, cur))
	    {
		/* match by command, class and name as second try */
		break;
	    }
	    else if (title && cur->title && strcmp (title, cur->title) == 0)
	    {
		/* last resort: match by window title */
		break;
	    }
	}
    }

    if (clientId)
	free (clientId);
    if (command)
	free (command);
    if (title)
	free (title);
    if (role)
	free (role);

    if (!cur)
	return FALSE;

    /* found a window */

    changeWindowState (w, (w->state & ~SAVED_WINDOW_STATE) | cur->state);

    if (cur->geometryValid)
    {
	xwcm = CWX | CWY;

	xwc.x = cur->geometry.x + w->input.left;
	xwc.y = cur->geometry.y + w->input.top;

	if (!sessionWindowIsOnAllViewports (w))
	{
	    xwc.x -= (w->screen->x * w->screen->width);
	    xwc.y -= (w->screen->y * w->screen->height);
	}

	if (cur->geometry.width != w->serverWidth)
	{
	    xwc.width = cur->geometry.width;
	    xwcm |= CWWidth;
	}
	if (cur->geometry.height != w->serverHeight)
	{
	    xwc.height = cur->geometry.height;
	    xwcm |= CWHeight;
	}

	if (w->mapNum && (xwcm & (CWWidth | CWHeight)))
	    sendSyncRequest (w);

	configureXWindow (w, xwcm, &xwc);
	w->placed = TRUE;
    }

    if (cur->minimized)
	minimizeWindow (w);

    if (cur->workspace != -1)
	setDesktopForWindow (w, cur->workspace);

    updateWindowAttributes (w, CompStackingUpdateModeNone);

    /* remove item from list */
    sessionRemoveWindowListItem (cur);

    return TRUE;
}
示例#7
0
static Bool
decorWindowUpdate (CompWindow *w,
		   Bool	      allowDecoration)
{
    WindowDecoration *wd;
    Decoration	     *old, *decor = NULL;
    Bool	     decorate = FALSE;
    CompMatch	     *match;
    int		     moveDx, moveDy;
    int		     oldShiftX = 0;
    int		     oldShiftY  = 0;

    DECOR_DISPLAY (w->screen->display);
    DECOR_SCREEN (w->screen);
    DECOR_WINDOW (w);

    wd = dw->wd;
    old = (wd) ? wd->decor : NULL;

    switch (w->type) {
    case CompWindowTypeDialogMask:
    case CompWindowTypeModalDialogMask:
    case CompWindowTypeUtilMask:
    case CompWindowTypeMenuMask:
    case CompWindowTypeNormalMask:
	if (w->mwmDecor & (MwmDecorAll | MwmDecorTitle))
	    decorate = TRUE;
    default:
	break;
    }

    if (w->wmType & (CompWindowTypeDockMask | CompWindowTypeDesktopMask))
	decorate = FALSE;

    if (w->attrib.override_redirect)
	decorate = FALSE;

    if (decorate)
    {
	match = &dd->opt[DECOR_DISPLAY_OPTION_DECOR_MATCH].value.match;
	if (!matchEval (match, w))
	    decorate = FALSE;
    }

    if (decorate)
    {
	if (dw->decor && decorCheckSize (w, dw->decor))
	{
	    decor = dw->decor;
	}
	else
	{
	    if (w->id == w->screen->display->activeWindow)
		decor = ds->decor[DECOR_ACTIVE];
	    else
		decor = ds->decor[DECOR_NORMAL];
	}
    }
    else
    {
	match = &dd->opt[DECOR_DISPLAY_OPTION_SHADOW_MATCH].value.match;
	if (matchEval (match, w))
	{
	    if (w->region->numRects == 1)
		decor = ds->decor[DECOR_BARE];

	    if (decor)
	    {
		if (!decorCheckSize (w, decor))
		    decor = NULL;
	    }
	}
    }

    if (!ds->dmWin || !allowDecoration)
	decor = NULL;

    if (decor == old)
	return FALSE;

    damageWindowOutputExtents (w);

    if (old)
    {
	oldShiftX = decorWindowShiftX (w);
	oldShiftY = decorWindowShiftY (w);

	destroyWindowDecoration (w->screen, wd);
    }

    if (decor)
    {
	dw->wd = createWindowDecoration (decor);
	if (!dw->wd)
	    return FALSE;

	if ((w->state & MAXIMIZE_STATE) == MAXIMIZE_STATE)
	    setWindowFrameExtents (w, &decor->maxInput);
	else
	    setWindowFrameExtents (w, &decor->input);

	moveDx = decorWindowShiftX (w) - oldShiftX;
	moveDy = decorWindowShiftY (w) - oldShiftY;

	updateWindowOutputExtents (w);
	damageWindowOutputExtents (w);
	updateWindowDecorationScale (w);
    }
    else
    {
	CompWindowExtents emptyInput;

	memset (&emptyInput, 0, sizeof (emptyInput));
	setWindowFrameExtents (w, &emptyInput);

	dw->wd = NULL;

	moveDx = -oldShiftX;
	moveDy = -oldShiftY;
    }

    if (w->placed && !w->attrib.override_redirect && (moveDx || moveDy))
    {
	XWindowChanges xwc;
	unsigned int   mask = CWX | CWY;

	xwc.x = w->serverX + moveDx;
	xwc.y = w->serverY + moveDy;

	if (w->state & CompWindowStateFullscreenMask)
	    mask &= ~(CWX | CWY);

	if (w->state & CompWindowStateMaximizedHorzMask)
	    mask &= ~CWX;

	if (w->state & CompWindowStateMaximizedVertMask)
	    mask &= ~CWY;

	if (w->saveMask & CWX)
	    w->saveWc.x += moveDx;

	if (w->saveMask & CWY)
	    w->saveWc.y += moveDy;

	if (mask)
	    configureXWindow (w, mask, &xwc);
    }

    return TRUE;
}
static void
gridCommonWindow (CompWindow *cw,
                  GridType   where)
{
    GRID_SCREEN (cw->screen);

    if ((cw) && (where != GridUnknown))
    {
        /* add maximize option */
        if (where == GridMaximize)
        {
            sendMaximizationRequest (cw);
            /* maximizeWindow (cw, MAXIMIZE_STATE); */
        }
        else
        {
            unsigned int valueMask = 0;
            int desiredState = 0;

            getTargetRect (cw, where);

            XWindowChanges xwc;

            /* if keys are pressed again then cycle through 1/3 or 2/3 widths... */

            /* Get current rect not including decorations */
            gs->currentRect.x = cw->serverX;
            gs->currentRect.y = cw->serverY;
            gs->currentRect.width  = cw->serverWidth;
            gs->currentRect.height = cw->serverHeight;
            DEBUG_RECT (currentRect);

            if ((gs->desiredRect.y == gs->currentRect.y &&
                    gs->desiredRect.height == gs->currentRect.height) &&
                    gridGetCycleSizes(cw->screen->display))
            {
                int slotWidth33 = gs->workarea.width / 3;
                int slotWidth66 = gs->workarea.width - slotWidth33;

                DEBUG_PRINT ((gridOut, "Multi!\n"));

                if (gs->props.numCellsX == 2) /* keys (1, 4, 7, 3, 6, 9) */
                {
                    if (gs->currentRect.width == gs->desiredRect.width &&
                            gs->currentRect.x == gs->desiredRect.x)
                    {
                        gs->desiredSlot.width = slotWidth66;
                        gs->desiredSlot.x = gs->workarea.x +
                                            gs->props.gravityRight * slotWidth33;
                    }
                    else
                    {
                        /* tricky, have to allow for window constraints when
                         * computing what the 33% and 66% offsets would be
                         */
                        XRectangle rect33, rect66, slot33, slot66;

                        slot33 = gs->desiredSlot;
                        slot33.x = gs->workarea.x +
                                   gs->props.gravityRight * slotWidth66;
                        slot33.width = slotWidth33;
                        constrainSize (cw, &slot33, &rect33);
                        DEBUG_RECT (slot33);
                        DEBUG_RECT (rect33);

                        slot66 = gs->desiredSlot;
                        slot66.x = gs->workarea.x +
                                   gs->props.gravityRight * slotWidth33;
                        slot66.width = slotWidth66;
                        constrainSize (cw, &slot66, &rect66);
                        DEBUG_RECT (slot66);
                        DEBUG_RECT (rect66);

                        if (gs->currentRect.width == rect66.width &&
                                gs->currentRect.x == rect66.x)
                        {
                            gs->desiredSlot.width = slotWidth33;
                            gs->desiredSlot.x = gs->workarea.x +
                                                gs->props.gravityRight * slotWidth66;
                        }
                    }
                }
                else /* keys (2, 5, 8) */
                {
                    if (gs->currentRect.width == gs->desiredRect.width &&
                            gs->currentRect.x == gs->desiredRect.x)
                    {
                        gs->desiredSlot.width = slotWidth33;
                        gs->desiredSlot.x = gs->workarea.x + slotWidth33;
                    }
                }
                constrainSize (cw, &gs->desiredSlot, &gs->desiredRect);
                DEBUG_RECT (gs->desiredRect);
            }

            xwc.x = gs->desiredRect.x;
            xwc.y = gs->desiredRect.y;
            xwc.width  = gs->desiredRect.width;
            xwc.height = gs->desiredRect.height;

            if (cw->mapNum)
                sendSyncRequest (cw);

            if (where == GridRight || where == GridLeft)
            {
                desiredState = CompWindowStateMaximizedVertMask;
                valueMask = CWX | CWWidth;
            }
            else if (where == GridTop || where == GridBottom)
            {
                desiredState = CompWindowStateMaximizedHorzMask;
                valueMask = CWY | CWHeight;
            }
            else
            {
                desiredState = 0;
                valueMask = CWX | CWY | CWWidth | CWHeight;
            }

            if (cw->state != desiredState)
                maximizeWindow (cw, desiredState);

            /* TODO: animate move+resize */
            configureXWindow (cw, valueMask, &xwc);

        }
    }
}
示例#9
0
文件: grid.c 项目: jordigh/fusilli
static Bool
gridPlaceWindow (Window          xid,
                 GridType        where)
{
	CompWindow *w;

	w  = findWindowAtDisplay (xid);
	if (w)
	{
		XRectangle     workarea;
		XRectangle     desiredSlot;
		XRectangle     desiredRect;
		XRectangle     currentRect;
		GridProps      props = gridProps[where];
		XWindowChanges xwc;

		/* get current available area */
		getWorkareaForOutput (w->screen, outputDeviceForWindow(w), &workarea);

		/* Convention:
		 * xxxSlot include decorations (it's the screen area occupied)
		 * xxxRect are undecorated (it's the constrained position
		                            of the contents)
		 */

		/* slice and dice to get desired slot - including decorations */
		desiredSlot.y =  workarea.y + props.gravityDown *
		                 (workarea.height / props.numCellsY);
		desiredSlot.height = workarea.height / props.numCellsY;
		desiredSlot.x =  workarea.x + props.gravityRight *
		                 (workarea.width / props.numCellsX);
		desiredSlot.width = workarea.width / props.numCellsX;

		/* Adjust for constraints and decorations */
		constrainSize (w, &desiredSlot, &desiredRect);

		/* Get current rect not including decorations */
		currentRect.x = w->serverX;
		currentRect.y = w->serverY;
		currentRect.width  = w->serverWidth;
		currentRect.height = w->serverHeight;

		if (desiredRect.y == currentRect.y &&
		    desiredRect.height == currentRect.height)
		{
			int slotWidth33  = workarea.width / 3;
			int slotWidth66  = workarea.width - slotWidth33;

			if (props.numCellsX == 2) /* keys (1, 4, 7, 3, 6, 9) */
			{
				if (currentRect.width == desiredRect.width &&
				    currentRect.x == desiredRect.x)
				{
					desiredSlot.width = slotWidth66;
					desiredSlot.x = workarea.x +
					        props.gravityRight * slotWidth33;
				}
				else
				{
					/* tricky, have to allow for window constraints when
					 * computing what the 33% and 66% offsets would be
					 */
					XRectangle rect33, rect66, slot33, slot66;

					slot33 = desiredSlot;
					slot33.x = workarea.x + props.gravityRight * slotWidth66;
					slot33.width = slotWidth33;
					constrainSize (w, &slot33, &rect33);

					slot66 = desiredSlot;
					slot66.x = workarea.x + props.gravityRight * slotWidth33;
					slot66.width = slotWidth66;
					constrainSize (w, &slot66, &rect66);

					if (currentRect.width == rect66.width &&
					    currentRect.x == rect66.x)
					{
						desiredSlot.width = slotWidth33;
						desiredSlot.x = workarea.x +
						    props.gravityRight * slotWidth66;
					}
				}
			}
			else /* keys (2, 5, 8) */
			{
				if (currentRect.width == desiredRect.width &&
				    currentRect.x == desiredRect.x)
				{
				    desiredSlot.width = slotWidth33;
				    desiredSlot.x = workarea.x + slotWidth33;
				}
			}
			constrainSize (w, &desiredSlot, &desiredRect);
		}

		xwc.x = desiredRect.x;
		xwc.y = desiredRect.y;
		xwc.width  = desiredRect.width;
		xwc.height = desiredRect.height;

		if (w->mapNum)
			sendSyncRequest (w);

		if (w->state & MAXIMIZE_STATE)
		{
			/* maximized state interferes with us, clear it */
			maximizeWindow (w, 0);
		}

		/* TODO: animate move+resize */
		configureXWindow (w, CWX | CWY | CWWidth | CWHeight, &xwc);
	}

	return TRUE;
}
示例#10
0
void
groupWindowUngrabNotify (CompWindow *w)
{
	CompScreen *s = w->screen;

	GROUP_SCREEN (s);
	GROUP_DISPLAY (&display);
	GROUP_WINDOW (w);

	if (gw->group && !gd->ignoreMode && !gs->queued)
	{
		int i;
		XRectangle rect;

		groupDequeueMoveNotifies (s);

		if (gd->resizeInfo)
		{
			rect.x      = WIN_X (w);
			rect.y      = WIN_Y (w);
			rect.width  = WIN_WIDTH (w);
			rect.height = WIN_HEIGHT (w);
		}

		for (i = 0; i < gw->group->nWins; i++)
		{
			CompWindow *cw = gw->group->windows[i];
			if (!cw)
				continue;

			if (cw->id != w->id)
			{
				GROUP_WINDOW (cw);

				if (gw->resizeGeometry)
				{
					unsigned int mask;

					gw->resizeGeometry->x      = WIN_X (cw);
					gw->resizeGeometry->y      = WIN_Y (cw);
					gw->resizeGeometry->width  = WIN_WIDTH (cw);
					gw->resizeGeometry->height = WIN_HEIGHT (cw);

					mask = groupUpdateResizeRectangle (cw, &rect, FALSE);
					if (mask)
					{
						XWindowChanges xwc;
						xwc.x      = gw->resizeGeometry->x;
						xwc.y      = gw->resizeGeometry->y;
						xwc.width  = gw->resizeGeometry->width;
						xwc.height = gw->resizeGeometry->height;

						if (w->mapNum && (mask & (CWWidth | CWHeight)))
							sendSyncRequest (w);

						configureXWindow (cw, mask, &xwc);
					}
					else
					{
						free (gw->resizeGeometry);
						gw->resizeGeometry =  NULL;
					}
				}
				if (gw->needsPosSync)
				{
					syncWindowPosition (cw);
					gw->needsPosSync = FALSE;
				}
				groupEnqueueUngrabNotify (cw);
			}
		}

		if (gd->resizeInfo)
		{
			free (gd->resizeInfo);
			gd->resizeInfo = NULL;
		}

		gw->group->grabWindow = None;
		gw->group->grabMask = 0;
	}

	UNWRAP (gs, s, windowUngrabNotify);
	(*s->windowUngrabNotify)(w);
	WRAP ( gs, s, windowUngrabNotify, groupWindowUngrabNotify);
}