コード例 #1
0
ファイル: mivaltree.c プロジェクト: 4eremuxa/xserver
/*
 * Compute the visibility of a shaped window
 */
int
miShapedWindowIn (RegionPtr universe, RegionPtr bounding,
                  BoxPtr rect, int x, int y)
{
    BoxRec  	box;
    BoxPtr	boundBox;
    int		nbox;
    Bool	someIn, someOut;
    int 	t, x1, y1, x2, y2;

    nbox = RegionNumRects (bounding);
    boundBox = RegionRects (bounding);
    someIn = someOut = FALSE;
    x1 = rect->x1;
    y1 = rect->y1;
    x2 = rect->x2;
    y2 = rect->y2;
    while (nbox--)
    {
	if ((t = boundBox->x1 + x) < x1)
	    t = x1;
	box.x1 = t;
	if ((t = boundBox->y1 + y) < y1)
	    t = y1;
	box.y1 = t;
	if ((t = boundBox->x2 + x) > x2)
	    t = x2;
	box.x2 = t;
	if ((t = boundBox->y2 + y) > y2)
	    t = y2;
	box.y2 = t;
	if (box.x1 > box.x2)
	    box.x2 = box.x1;
	if (box.y1 > box.y2)
	    box.y2 = box.y1;
	switch (RegionContainsRect(universe, &box))
	{
	case rgnIN:
	    if (someOut)
		return rgnPART;
	    someIn = TRUE;
	    break;
	case rgnOUT:
	    if (someIn)
		return rgnPART;
	    someOut = TRUE;
	    break;
	default:
	    return rgnPART;
	}
	boundBox++;
    }
    if (someIn)
	return rgnIN;
    return rgnOUT;
}
コード例 #2
0
ファイル: fbglyph.c プロジェクト: 01org/iotg-lin-gfx-ddx
static bool
fbGlyphIn(GCPtr gc, int x, int y, int width, int height)
{
	BoxRec box;
	BoxPtr extents = RegionExtents(gc->pCompositeClip);

	/*
	 * Check extents by hand to avoid 16 bit overflows
	 */
	if (x < (int) extents->x1 || (int) extents->x2 < x + width)
		return FALSE;
	if (y < (int) extents->y1 || (int) extents->y2 < y + height)
		return FALSE;

	box.x1 = x;
	box.x2 = x + width;
	box.y1 = y;
	box.y2 = y + height;
	return RegionContainsRect(gc->pCompositeClip, &box) == rgnIN;
}
コード例 #3
0
ファイル: fbglyph.c プロジェクト: MrKepzie/xserver
Bool
fbGlyphIn(RegionPtr pRegion, int x, int y, int width, int height)
{
    BoxRec box;
    BoxPtr pExtents = RegionExtents(pRegion);

    /*
     * Check extents by hand to avoid 16 bit overflows
     */
    if (x < (int) pExtents->x1)
        return FALSE;
    if ((int) pExtents->x2 < x + width)
        return FALSE;
    if (y < (int) pExtents->y1)
        return FALSE;
    if ((int) pExtents->y2 < y + height)
        return FALSE;
    box.x1 = x;
    box.x2 = x + width;
    box.y1 = y;
    box.y2 = y + height;
    return RegionContainsRect(pRegion, &box) == rgnIN;
}
コード例 #4
0
ファイル: glamor_putimage.c プロジェクト: Distrotech/glamor
static Bool 
_glamor_put_image(DrawablePtr drawable, GCPtr gc, int depth, int x, int y,
		 int w, int h, int left_pad, int image_format, char *bits, Bool fallback)
{
	PixmapPtr pixmap = glamor_get_drawable_pixmap(drawable);
	glamor_pixmap_private *pixmap_priv =
	    glamor_get_pixmap_private(pixmap);
	RegionPtr clip;
	int x_off, y_off;
	Bool ret = FALSE;
	PixmapPtr temp_pixmap, sub_pixmap;
	glamor_pixmap_private *temp_pixmap_priv;
	BoxRec box;
	int stride;

	glamor_get_drawable_deltas(drawable, pixmap, &x_off, &y_off);
	clip = fbGetCompositeClip(gc);
	if (image_format == XYBitmap) {
		assert(depth == 1);
		goto fail;
	}

	if (!GLAMOR_PIXMAP_PRIV_HAS_FBO(pixmap_priv)) {
		glamor_fallback("has no fbo.\n");
		goto fail;
	}

	if (image_format != ZPixmap) {
		glamor_fallback("non-ZPixmap\n");
		goto fail;
	}

	if (!glamor_set_planemask(pixmap, gc->planemask)) {
		goto fail;
	}
	/* create a temporary pixmap and upload the bits to that
	 * pixmap, then apply clip copy it to the destination pixmap.*/
	stride = PixmapBytePad(w, depth);
	box.x1 = x + drawable->x;
	box.y1 = y + drawable->y;
	box.x2 = x + w + drawable->x;
	box.y2 = y + h + drawable->y;

	if ((clip != NULL && RegionContainsRect(clip, &box) != rgnIN)
	     || gc->alu != GXcopy) {
		temp_pixmap = glamor_create_pixmap(drawable->pScreen, w, h, depth, 0);
		if (temp_pixmap == NULL)
			goto fail;

		temp_pixmap_priv = glamor_get_pixmap_private(temp_pixmap);

		if (GLAMOR_PIXMAP_PRIV_IS_PICTURE(pixmap_priv)) {
			temp_pixmap_priv->base.picture = pixmap_priv->base.picture;
			temp_pixmap_priv->base.is_picture = pixmap_priv->base.is_picture;
		}

		glamor_upload_sub_pixmap_to_texture(temp_pixmap, 0, 0, w, h,
		                                    stride, bits, 0);
		glamor_copy_area(&temp_pixmap->drawable, drawable, gc, 0, 0, w, h, x, y);
		glamor_destroy_pixmap(temp_pixmap);
	} else {
		glamor_upload_sub_pixmap_to_texture(pixmap, x + drawable->x + x_off, y + drawable->y + y_off,
		                                    w, h, stride, bits, 0);
	}
	ret = TRUE;
	goto done;

fail:
	glamor_set_planemask(pixmap, ~0);

	if (!fallback
	    && glamor_ddx_fallback_check_pixmap(&pixmap->drawable))
		goto done;

	glamor_fallback("to %p (%c)\n",
			drawable, glamor_get_drawable_location(drawable));

	sub_pixmap = glamor_get_sub_pixmap(pixmap, x + x_off + drawable->x,
					   y + y_off + drawable->y, w, h,
					   GLAMOR_ACCESS_RW);
	if (sub_pixmap) {
		if (clip != NULL)
			pixman_region_translate (clip, -x - drawable->x, -y - drawable->y);

		fbPutImage(&sub_pixmap->drawable, gc, depth, 0, 0, w, h,
			   left_pad, image_format, bits);

		glamor_put_sub_pixmap(sub_pixmap, pixmap,
				      x + x_off + drawable->x,
				      y + y_off + drawable->y,
				      w, h, GLAMOR_ACCESS_RW);
		if (clip != NULL)
			pixman_region_translate (clip, x + drawable->x, y + drawable->y);
	} else
		fbPutImage(drawable, gc, depth, x, y, w, h,
			   left_pad, image_format, bits);
	ret = TRUE;

done:
	return ret;
}
コード例 #5
0
ファイル: mivaltree.c プロジェクト: 4eremuxa/xserver
/*
 *-----------------------------------------------------------------------
 * miComputeClips --
 *	Recompute the clipList, borderClip, exposed and borderExposed
 *	regions for pParent and its children. Only viewable windows are
 *	taken into account.
 *
 * Results:
 *	None.
 *
 * Side Effects:
 *	clipList, borderClip, exposed and borderExposed are altered.
 *	A VisibilityNotify event may be generated on the parent window.
 *
 *-----------------------------------------------------------------------
 */
static void
miComputeClips (
    WindowPtr	pParent,
    ScreenPtr	pScreen,
    RegionPtr	universe,
    VTKind		kind,
    RegionPtr		exposed ) /* for intermediate calculations */
{
    int			dx,
			dy;
    RegionRec		childUniverse;
    WindowPtr		pChild;
    int     	  	oldVis, newVis;
    BoxRec		borderSize;
    RegionRec		childUnion;
    Bool		overlap;
    RegionPtr		borderVisible;
    /*
     * Figure out the new visibility of this window.
     * The extent of the universe should be the same as the extent of
     * the borderSize region. If the window is unobscured, this rectangle
     * will be completely inside the universe (the universe will cover it
     * completely). If the window is completely obscured, none of the
     * universe will cover the rectangle.
     */
    borderSize.x1 = pParent->drawable.x - wBorderWidth(pParent);
    borderSize.y1 = pParent->drawable.y - wBorderWidth(pParent);
    dx = (int) pParent->drawable.x + (int) pParent->drawable.width + wBorderWidth(pParent);
    if (dx > 32767)
	dx = 32767;
    borderSize.x2 = dx;
    dy = (int) pParent->drawable.y + (int) pParent->drawable.height + wBorderWidth(pParent);
    if (dy > 32767)
	dy = 32767;
    borderSize.y2 = dy;

#ifdef COMPOSITE
    /*
     * In redirected drawing case, reset universe to borderSize
     */
    if (pParent->redirectDraw != RedirectDrawNone)
    {
	if (miSetRedirectBorderClipProc)
	{
	    if (TreatAsTransparent (pParent))
		RegionEmpty(universe);
	    (*miSetRedirectBorderClipProc) (pParent, universe);
	}
	RegionCopy(universe, &pParent->borderSize);
    }
#endif

    oldVis = pParent->visibility;
    switch (RegionContainsRect(universe, &borderSize))
    {
	case rgnIN:
	    newVis = VisibilityUnobscured;
	    break;
	case rgnPART:
	    newVis = VisibilityPartiallyObscured;
	    {
		RegionPtr   pBounding;

		if ((pBounding = wBoundingShape (pParent)))
		{
		    switch (miShapedWindowIn (universe, pBounding,
					      &borderSize,
					      pParent->drawable.x,
 					      pParent->drawable.y))
		    {
		    case rgnIN:
			newVis = VisibilityUnobscured;
			break;
		    case rgnOUT:
			newVis = VisibilityFullyObscured;
			break;
		    }
		}
	    }
	    break;
	default:
	    newVis = VisibilityFullyObscured;
	    break;
    }
    pParent->visibility = newVis;
    if (oldVis != newVis &&
	((pParent->eventMask | wOtherEventMasks(pParent)) & VisibilityChangeMask))
	SendVisibilityNotify(pParent);

    dx = pParent->drawable.x - pParent->valdata->before.oldAbsCorner.x;
    dy = pParent->drawable.y - pParent->valdata->before.oldAbsCorner.y;

    /*
     * avoid computations when dealing with simple operations
     */

    switch (kind) {
    case VTMap:
    case VTStack:
    case VTUnmap:
	break;
    case VTMove:
	if ((oldVis == newVis) &&
	    ((oldVis == VisibilityFullyObscured) ||
	     (oldVis == VisibilityUnobscured)))
	{
	    pChild = pParent;
	    while (1)
	    {
		if (pChild->viewable)
		{
		    if (pChild->visibility != VisibilityFullyObscured)
		    {
			RegionTranslate(&pChild->borderClip,
						      dx, dy);
			RegionTranslate(&pChild->clipList,
						      dx, dy);
			pChild->drawable.serialNumber = NEXT_SERIAL_NUMBER;
			if (pScreen->ClipNotify)
			    (* pScreen->ClipNotify) (pChild, dx, dy);

		    }
		    if (pChild->valdata)
		    {
			RegionNull(&pChild->valdata->after.borderExposed);
			if (HasParentRelativeBorder(pChild))
			{
			    RegionSubtract(&pChild->valdata->after.borderExposed,
					   &pChild->borderClip,
					   &pChild->winSize);
			}
			RegionNull(&pChild->valdata->after.exposed);
		    }
		    if (pChild->firstChild)
		    {
			pChild = pChild->firstChild;
			continue;
		    }
		}
		while (!pChild->nextSib && (pChild != pParent))
		    pChild = pChild->parent;
		if (pChild == pParent)
		    break;
		pChild = pChild->nextSib;
	    }
	    return;
	}
	/* fall through */
    default:
    	/*
     	 * To calculate exposures correctly, we have to translate the old
     	 * borderClip and clipList regions to the window's new location so there
     	 * is a correspondence between pieces of the new and old clipping regions.
     	 */
    	if (dx || dy) 
    	{
	    /*
	     * We translate the old clipList because that will be exposed or copied
	     * if gravity is right.
	     */
	    RegionTranslate(&pParent->borderClip, dx, dy);
	    RegionTranslate(&pParent->clipList, dx, dy);
    	} 
	break;
    case VTBroken:
	RegionEmpty(&pParent->borderClip);
	RegionEmpty(&pParent->clipList);
	break;
    }

    borderVisible = pParent->valdata->before.borderVisible;
    RegionNull(&pParent->valdata->after.borderExposed);
    RegionNull(&pParent->valdata->after.exposed);

    /*
     * Since the borderClip must not be clipped by the children, we do
     * the border exposure first...
     *
     * 'universe' is the window's borderClip. To figure the exposures, remove
     * the area that used to be exposed from the new.
     * This leaves a region of pieces that weren't exposed before.
     */

    if (HasBorder (pParent))
    {
    	if (borderVisible)
    	{
	    /*
	     * when the border changes shape, the old visible portions
	     * of the border will be saved by DIX in borderVisible --
	     * use that region and destroy it
	     */
	    RegionSubtract(exposed, universe, borderVisible);
	    RegionDestroy(borderVisible);
    	}
    	else
    	{
	    RegionSubtract(exposed, universe, &pParent->borderClip);
    	}
	if (HasParentRelativeBorder(pParent) && (dx || dy))
	    RegionSubtract(&pParent->valdata->after.borderExposed,
				  universe,
				  &pParent->winSize);
	else
	    RegionSubtract(&pParent->valdata->after.borderExposed,
			       exposed, &pParent->winSize);

	RegionCopy(&pParent->borderClip, universe);
    
    	/*
     	 * To get the right clipList for the parent, and to make doubly sure
     	 * that no child overlaps the parent's border, we remove the parent's
     	 * border from the universe before proceeding.
     	 */
    
	RegionIntersect(universe, universe, &pParent->winSize);
    }
    else
	RegionCopy(&pParent->borderClip, universe);
    
    if ((pChild = pParent->firstChild) && pParent->mapped)
    {
	RegionNull(&childUniverse);
	RegionNull(&childUnion);
	if ((pChild->drawable.y < pParent->lastChild->drawable.y) ||
	    ((pChild->drawable.y == pParent->lastChild->drawable.y) &&
	     (pChild->drawable.x < pParent->lastChild->drawable.x)))
	{
	    for (; pChild; pChild = pChild->nextSib)
	    {
		if (pChild->viewable && !TreatAsTransparent(pChild))
		    RegionAppend(&childUnion, &pChild->borderSize);
	    }
	}
	else
	{
	    for (pChild = pParent->lastChild; pChild; pChild = pChild->prevSib)
	    {
		if (pChild->viewable && !TreatAsTransparent(pChild))
		    RegionAppend(&childUnion, &pChild->borderSize);
	    }
	}
	RegionValidate(&childUnion, &overlap);

	for (pChild = pParent->firstChild;
	     pChild;
	     pChild = pChild->nextSib)
 	{
	    if (pChild->viewable) {
		/*
		 * If the child is viewable, we want to remove its extents
		 * from the current universe, but we only re-clip it if
		 * it's been marked.
		 */
		if (pChild->valdata) {
		    /*
		     * Figure out the new universe from the child's
		     * perspective and recurse.
		     */
		    RegionIntersect(&childUniverse,
					    universe,
					    &pChild->borderSize);
		    miComputeClips (pChild, pScreen, &childUniverse, kind,
				    exposed);
		}
		/*
		 * Once the child has been processed, we remove its extents
		 * from the current universe, thus denying its space to any
		 * other sibling.
		 */
		if (overlap && !TreatAsTransparent (pChild))
		    RegionSubtract(universe, universe,
					  &pChild->borderSize);
	    }
	}
	if (!overlap)
	    RegionSubtract(universe, universe, &childUnion);
	RegionUninit(&childUnion);
	RegionUninit(&childUniverse);
    } /* if any children */

    /*
     * 'universe' now contains the new clipList for the parent window.
     *
     * To figure the exposure of the window we subtract the old clip from the
     * new, just as for the border.
     */

    if (oldVis == VisibilityFullyObscured ||
	oldVis == VisibilityNotViewable)
    {
	RegionCopy(&pParent->valdata->after.exposed, universe);
    }
    else if (newVis != VisibilityFullyObscured &&
	     newVis != VisibilityNotViewable)
    {
	RegionSubtract(&pParent->valdata->after.exposed,
			       universe, &pParent->clipList);
    }

    /* HACK ALERT - copying contents of regions, instead of regions */
    {
	RegionRec   tmp;

	tmp = pParent->clipList;
	pParent->clipList = *universe;
	*universe = tmp;
    }

#ifdef NOTDEF
    RegionCopy(&pParent->clipList, universe);
#endif

    pParent->drawable.serialNumber = NEXT_SERIAL_NUMBER;

    if (pScreen->ClipNotify)
	(* pScreen->ClipNotify) (pParent, dx, dy);
}
コード例 #6
0
ファイル: rdpdraw.c プロジェクト: mehulsbhatt/xrdp
/* return 2, draw using clip */
int
rdp_get_clip(RegionPtr pRegion, DrawablePtr pDrawable, GCPtr pGC)
{
  WindowPtr pWindow;
  RegionPtr temp;
  BoxRec box;
  int rv;

  rv = 0;
  if (pDrawable->type == DRAWABLE_PIXMAP)
  {
    switch (pGC->clientClipType)
    {
      case CT_NONE:
        rv = 1;
        break;
      case CT_REGION:
        rv = 2;
        RegionCopy(pRegion, pGC->clientClip);
        break;
      default:
        rdpLog("unimp clip type %d\n", pGC->clientClipType);
        break;
    }
    if (rv == 2) /* check if the clip is the entire pixmap */
    {
      box.x1 = 0;
      box.y1 = 0;
      box.x2 = pDrawable->width;
      box.y2 = pDrawable->height;
      if (RegionContainsRect(pRegion, &box) == rgnIN)
      {
        rv = 1;
      }
    }
  }
  else if (pDrawable->type == DRAWABLE_WINDOW)
  {
    pWindow = (WindowPtr)pDrawable;
    if (pWindow->viewable)
    {
      if (pGC->subWindowMode == IncludeInferiors)
      {
        temp = &pWindow->borderClip;
      }
      else
      {
        temp = &pWindow->clipList;
      }
      if (RegionNotEmpty(temp))
      {
        switch (pGC->clientClipType)
        {
          case CT_NONE:
            rv = 2;
            RegionCopy(pRegion, temp);
            break;
          case CT_REGION:
            rv = 2;
            RegionCopy(pRegion, pGC->clientClip);
            RegionTranslate(pRegion,
                            pDrawable->x + pGC->clipOrg.x,
                            pDrawable->y + pGC->clipOrg.y);
            RegionIntersect(pRegion, pRegion, temp);
            break;
          default:
            rdpLog("unimp clip type %d\n", pGC->clientClipType);
            break;
        }
        if (rv == 2) /* check if the clip is the entire screen */
        {
          box.x1 = 0;
          box.y1 = 0;
          box.x2 = g_rdpScreen.width;
          box.y2 = g_rdpScreen.height;
          if (RegionContainsRect(pRegion, &box) == rgnIN)
          {
            rv = 1;
          }
        }
      }
    }
  }
  return rv;
}
コード例 #7
0
ファイル: miexpose.c プロジェクト: mirror/xserver
RegionPtr
miHandleExposures(DrawablePtr pSrcDrawable, DrawablePtr pDstDrawable,
                  GCPtr pGC, int srcx, int srcy, int width, int height,
                  int dstx, int dsty)
{
    RegionPtr prgnSrcClip;      /* drawable-relative source clip */
    RegionRec rgnSrcRec;
    RegionPtr prgnDstClip;      /* drawable-relative dest clip */
    RegionRec rgnDstRec;
    BoxRec srcBox;              /* unclipped source */
    RegionRec rgnExposed;       /* exposed region, calculated source-
                                   relative, made dst relative to
                                   intersect with visible parts of
                                   dest and send events to client,
                                   and then screen relative to paint
                                   the window background
                                 */
    WindowPtr pSrcWin;
    BoxRec expBox = { 0, };
    Bool extents;

    /* avoid work if we can */
    if (!pGC->graphicsExposures && pDstDrawable->type == DRAWABLE_PIXMAP)
        return NULL;

    srcBox.x1 = srcx;
    srcBox.y1 = srcy;
    srcBox.x2 = srcx + width;
    srcBox.y2 = srcy + height;

    if (pSrcDrawable->type != DRAWABLE_PIXMAP) {
        BoxRec TsrcBox;

        TsrcBox.x1 = srcx + pSrcDrawable->x;
        TsrcBox.y1 = srcy + pSrcDrawable->y;
        TsrcBox.x2 = TsrcBox.x1 + width;
        TsrcBox.y2 = TsrcBox.y1 + height;
        pSrcWin = (WindowPtr) pSrcDrawable;
        if (pGC->subWindowMode == IncludeInferiors) {
            prgnSrcClip = NotClippedByChildren(pSrcWin);
            if ((RegionContainsRect(prgnSrcClip, &TsrcBox)) == rgnIN) {
                RegionDestroy(prgnSrcClip);
                return NULL;
            }
        }
        else {
            if ((RegionContainsRect(&pSrcWin->clipList, &TsrcBox)) == rgnIN)
                return NULL;
            prgnSrcClip = &rgnSrcRec;
            RegionNull(prgnSrcClip);
            RegionCopy(prgnSrcClip, &pSrcWin->clipList);
        }
        RegionTranslate(prgnSrcClip, -pSrcDrawable->x, -pSrcDrawable->y);
    }
    else {
        BoxRec box;

        if ((srcBox.x1 >= 0) && (srcBox.y1 >= 0) &&
            (srcBox.x2 <= pSrcDrawable->width) &&
            (srcBox.y2 <= pSrcDrawable->height))
            return NULL;

        box.x1 = 0;
        box.y1 = 0;
        box.x2 = pSrcDrawable->width;
        box.y2 = pSrcDrawable->height;
        prgnSrcClip = &rgnSrcRec;
        RegionInit(prgnSrcClip, &box, 1);
        pSrcWin = NULL;
    }

    if (pDstDrawable == pSrcDrawable) {
        prgnDstClip = prgnSrcClip;
    }
    else if (pDstDrawable->type != DRAWABLE_PIXMAP) {
        if (pGC->subWindowMode == IncludeInferiors) {
            prgnDstClip = NotClippedByChildren((WindowPtr) pDstDrawable);
        }
        else {
            prgnDstClip = &rgnDstRec;
            RegionNull(prgnDstClip);
            RegionCopy(prgnDstClip, &((WindowPtr) pDstDrawable)->clipList);
        }
        RegionTranslate(prgnDstClip, -pDstDrawable->x, -pDstDrawable->y);
    }
    else {
        BoxRec box;

        box.x1 = 0;
        box.y1 = 0;
        box.x2 = pDstDrawable->width;
        box.y2 = pDstDrawable->height;
        prgnDstClip = &rgnDstRec;
        RegionInit(prgnDstClip, &box, 1);
    }

    /* drawable-relative source region */
    RegionInit(&rgnExposed, &srcBox, 1);

    /* now get the hidden parts of the source box */
    RegionSubtract(&rgnExposed, &rgnExposed, prgnSrcClip);

    /* move them over the destination */
    RegionTranslate(&rgnExposed, dstx - srcx, dsty - srcy);

    /* intersect with visible areas of dest */
    RegionIntersect(&rgnExposed, &rgnExposed, prgnDstClip);

    /* intersect with client clip region. */
    if (pGC->clientClip)
        RegionIntersect(&rgnExposed, &rgnExposed, pGC->clientClip);

    /*
     * If we have LOTS of rectangles, we decide to take the extents
     * and force an exposure on that.  This should require much less
     * work overall, on both client and server.  This is cheating, but
     * isn't prohibited by the protocol ("spontaneous combustion" :-)
     * for windows.
     */
    extents = pGC->graphicsExposures &&
        (RegionNumRects(&rgnExposed) > RECTLIMIT) &&
        (pDstDrawable->type != DRAWABLE_PIXMAP);
    if (pSrcWin) {
        RegionPtr region;

        if (!(region = wClipShape(pSrcWin)))
            region = wBoundingShape(pSrcWin);
        /*
         * If you try to CopyArea the extents of a shaped window, compacting the
         * exposed region will undo all our work!
         */
        if (extents && pSrcWin && region &&
            (RegionContainsRect(region, &srcBox) != rgnIN))
            extents = FALSE;
    }
    if (extents) {
        expBox = *RegionExtents(&rgnExposed);
        RegionReset(&rgnExposed, &expBox);
    }
    if ((pDstDrawable->type != DRAWABLE_PIXMAP) &&
        (((WindowPtr) pDstDrawable)->backgroundState != None)) {
        WindowPtr pWin = (WindowPtr) pDstDrawable;

        /* make the exposed area screen-relative */
        RegionTranslate(&rgnExposed, pDstDrawable->x, pDstDrawable->y);

        if (extents) {
            /* PaintWindow doesn't clip, so we have to */
            RegionIntersect(&rgnExposed, &rgnExposed, &pWin->clipList);
        }
        pDstDrawable->pScreen->PaintWindow((WindowPtr) pDstDrawable,
                                           &rgnExposed, PW_BACKGROUND);

        if (extents) {
            RegionReset(&rgnExposed, &expBox);
        }
        else
            RegionTranslate(&rgnExposed, -pDstDrawable->x, -pDstDrawable->y);
    }
    if (prgnDstClip == &rgnDstRec) {
        RegionUninit(prgnDstClip);
    }
    else if (prgnDstClip != prgnSrcClip) {
        RegionDestroy(prgnDstClip);
    }

    if (prgnSrcClip == &rgnSrcRec) {
        RegionUninit(prgnSrcClip);
    }
    else {
        RegionDestroy(prgnSrcClip);
    }

    if (pGC->graphicsExposures) {
        /* don't look */
        RegionPtr exposed = RegionCreate(NullBox, 0);

        *exposed = rgnExposed;
        return exposed;
    }
    else {
        RegionUninit(&rgnExposed);
        return NULL;
    }
}
コード例 #8
0
ファイル: miwindow.c プロジェクト: mmaruska/xserver
Bool
miMarkOverlappedWindows(WindowPtr pWin, WindowPtr pFirst, WindowPtr *ppLayerWin)
{
    BoxPtr box;
    WindowPtr pChild, pLast;
    Bool anyMarked = FALSE;
    MarkWindowProcPtr MarkWindow = pWin->drawable.pScreen->MarkWindow;

    /* single layered systems are easy */
    if (ppLayerWin)
        *ppLayerWin = pWin;

    if (pWin == pFirst) {
        /* Blindly mark pWin and all of its inferiors.   This is a slight
         * overkill if there are mapped windows that outside pWin's border,
         * but it's better than wasting time on RectIn checks.
         */
        pChild = pWin;
        while (1) {
            if (pChild->viewable) {
                if (RegionBroken(&pChild->winSize))
                    SetWinSize(pChild);
                if (RegionBroken(&pChild->borderSize))
                    SetBorderSize(pChild);
                (*MarkWindow) (pChild);
                if (pChild->firstChild) {
                    pChild = pChild->firstChild;
                    continue;
                }
            }
            while (!pChild->nextSib && (pChild != pWin))
                pChild = pChild->parent;
            if (pChild == pWin)
                break;
            pChild = pChild->nextSib;
        }
        anyMarked = TRUE;
        pFirst = pFirst->nextSib;
    }
    if ((pChild = pFirst)) {
        box = RegionExtents(&pWin->borderSize);
        pLast = pChild->parent->lastChild;
        while (1) {
            if (pChild->viewable) {
                if (RegionBroken(&pChild->winSize))
                    SetWinSize(pChild);
                if (RegionBroken(&pChild->borderSize))
                    SetBorderSize(pChild);
                if (RegionContainsRect(&pChild->borderSize, box)) {
                    (*MarkWindow) (pChild);
                    anyMarked = TRUE;
                    if (pChild->firstChild) {
                        pChild = pChild->firstChild;
                        continue;
                    }
                }
            }
            while (!pChild->nextSib && (pChild != pLast))
                pChild = pChild->parent;
            if (pChild == pLast)
                break;
            pChild = pChild->nextSib;
        }
    }
    if (anyMarked)
        (*MarkWindow) (pWin->parent);
    return anyMarked;
}