diff --git a/fb/fb.h b/fb/fb.h index 37de71ea5..8b2839aab 100644 --- a/fb/fb.h +++ b/fb/fb.h @@ -700,38 +700,41 @@ typedef struct { #define __fbPixOffXPix(pPix) (__fbPixDrawableX(pPix)) #define __fbPixOffYPix(pPix) (__fbPixDrawableY(pPix)) -#define fbGetDrawable(pDrawable, pointer, stride, bpp, xoff, yoff) { \ - PixmapPtr _pPix; \ - if ((pDrawable)->type != DRAWABLE_PIXMAP) { \ - _pPix = fbGetWindowPixmap(pDrawable); \ - (xoff) = __fbPixOffXWin(_pPix); \ - (yoff) = __fbPixOffYWin(_pPix); \ - } else { \ - _pPix = (PixmapPtr) (pDrawable); \ - (xoff) = __fbPixOffXPix(_pPix); \ - (yoff) = __fbPixOffYPix(_pPix); \ - } \ - fbPrepareAccess(pDrawable); \ - (pointer) = (FbBits *) _pPix->devPrivate.ptr; \ - (stride) = ((int) _pPix->devKind) / sizeof (FbBits); (void)(stride); \ - (bpp) = _pPix->drawable.bitsPerPixel; (void)(bpp); \ +#define fbGetDrawablePixmap(pDrawable, pixmap, xoff, yoff) { \ + if ((pDrawable)->type != DRAWABLE_PIXMAP) { \ + (pixmap) = fbGetWindowPixmap(pDrawable); \ + (xoff) = __fbPixOffXWin(pixmap); \ + (yoff) = __fbPixOffYWin(pixmap); \ + } else { \ + (pixmap) = (PixmapPtr) (pDrawable); \ + (xoff) = __fbPixOffXPix(pixmap); \ + (yoff) = __fbPixOffYPix(pixmap); \ + } \ + fbPrepareAccess(pDrawable); \ } -#define fbGetStipDrawable(pDrawable, pointer, stride, bpp, xoff, yoff) { \ - PixmapPtr _pPix; \ - if ((pDrawable)->type != DRAWABLE_PIXMAP) { \ - _pPix = fbGetWindowPixmap(pDrawable); \ - (xoff) = __fbPixOffXWin(_pPix); \ - (yoff) = __fbPixOffYWin(_pPix); \ - } else { \ - _pPix = (PixmapPtr) (pDrawable); \ - (xoff) = __fbPixOffXPix(_pPix); \ - (yoff) = __fbPixOffYPix(_pPix); \ - } \ - fbPrepareAccess(pDrawable); \ - (pointer) = (FbStip *) _pPix->devPrivate.ptr; \ - (stride) = ((int) _pPix->devKind) / sizeof (FbStip); (void)(stride); \ - (bpp) = _pPix->drawable.bitsPerPixel; (void)(bpp); \ +#define fbGetPixmapBitsData(pixmap, pointer, stride, bpp) { \ + (pointer) = (FbBits *) (pixmap)->devPrivate.ptr; \ + (stride) = ((int) (pixmap)->devKind) / sizeof (FbBits); (void)(stride); \ + (bpp) = (pixmap)->drawable.bitsPerPixel; (void)(bpp); \ +} + +#define fbGetPixmapStipData(pixmap, pointer, stride, bpp) { \ + (pointer) = (FbStip *) (pixmap)->devPrivate.ptr; \ + (stride) = ((int) (pixmap)->devKind) / sizeof (FbStip); (void)(stride); \ + (bpp) = (pixmap)->drawable.bitsPerPixel; (void)(bpp); \ +} + +#define fbGetDrawable(pDrawable, pointer, stride, bpp, xoff, yoff) { \ + PixmapPtr _pPix; \ + fbGetDrawablePixmap(pDrawable, _pPix, xoff, yoff); \ + fbGetPixmapBitsData(_pPix, pointer, stride, bpp); \ +} + +#define fbGetStipDrawable(pDrawable, pointer, stride, bpp, xoff, yoff) { \ + PixmapPtr _pPix; \ + fbGetDrawablePixmap(pDrawable, _pPix, xoff, yoff); \ + fbGetPixmapStipData(_pPix, pointer, stride, bpp); \ } /* @@ -2079,9 +2082,16 @@ fbFillRegionSolid (DrawablePtr pDrawable, FbBits xor); extern _X_EXPORT pixman_image_t * -image_from_pict (PicturePtr pict, - Bool has_clip, - Bool is_src); +image_from_pict (PicturePtr pict, + Bool has_clip, + Bool is_src); + +extern _X_EXPORT pixman_image_t * +image_from_pict_18 (PicturePtr pict, + Bool has_clip, + int *xoff, + int *yoff); + extern _X_EXPORT void free_pixman_pict (PicturePtr, pixman_image_t *); #endif /* _FB_H_ */ diff --git a/fb/fbpict.c b/fb/fbpict.c index 8fdaa584e..f9f4343f7 100644 --- a/fb/fbpict.c +++ b/fb/fbpict.c @@ -158,19 +158,24 @@ fbComposite (CARD8 op, CARD16 height) { pixman_image_t *src, *mask, *dest; + int src_xoff, src_yoff; + int msk_xoff, msk_yoff; + int dst_xoff, dst_yoff; - miCompositeSourceValidate (pSrc, xSrc, ySrc, width, height); + miCompositeSourceValidate (pSrc, xSrc - xDst, ySrc - yDst, width, height); if (pMask) - miCompositeSourceValidate (pMask, xMask, yMask, width, height); + miCompositeSourceValidate (pMask, xMask - xDst, yMask - yDst, width, height); - src = image_from_pict (pSrc, TRUE, TRUE); - mask = image_from_pict (pMask, TRUE, TRUE); - dest = image_from_pict (pDst, TRUE, FALSE); + src = image_from_pict_18 (pSrc, FALSE, &src_xoff, &src_yoff); + mask = image_from_pict_18 (pMask, FALSE, &msk_xoff, &msk_yoff); + dest = image_from_pict_18 (pDst, TRUE, &dst_xoff, &dst_yoff); if (src && dest && !(pMask && !mask)) { pixman_image_composite (op, src, mask, dest, - xSrc, ySrc, xMask, yMask, xDst, yDst, + xSrc + src_xoff, ySrc + src_yoff, + xMask + msk_xoff, yMask + msk_yoff, + xDst + dst_xoff, yDst + dst_yoff, width, height); } @@ -270,22 +275,22 @@ create_conical_gradient_image (PictGradient *gradient) static pixman_image_t * create_bits_picture (PicturePtr pict, - Bool has_clip) + Bool has_clip, + int *xoff, + int *yoff) { + PixmapPtr pixmap; FbBits *bits; FbStride stride; - int bpp, xoff, yoff; + int bpp; pixman_image_t *image; - fbGetDrawable (pict->pDrawable, bits, stride, bpp, xoff, yoff); - - bits = (FbBits*)((CARD8*)bits + - (pict->pDrawable->y + yoff) * stride * sizeof(FbBits) + - (pict->pDrawable->x + xoff) * (bpp / 8)); + fbGetDrawablePixmap (pict->pDrawable, pixmap, *xoff, *yoff); + fbGetPixmapBitsData(pixmap, bits, stride, bpp); image = pixman_image_create_bits ( pict->format, - pict->pDrawable->width, pict->pDrawable->height, + pixmap->drawable.width, pixmap->drawable.height, (uint32_t *)bits, stride * sizeof (FbStride)); @@ -311,30 +316,52 @@ create_bits_picture (PicturePtr pict, if (pict->clientClipType != CT_NONE) pixman_image_set_has_client_clip (image, TRUE); - pixman_region_translate (pict->pCompositeClip, - pict->pDrawable->x, - pict->pDrawable->y); + if (*xoff || *yoff) + pixman_region_translate (pict->pCompositeClip, *xoff, *yoff); pixman_image_set_clip_region (image, pict->pCompositeClip); - pixman_region_translate (pict->pCompositeClip, pict->pDrawable->x, pict->pDrawable->y); + if (*xoff || *yoff) + pixman_region_translate (pict->pCompositeClip, -*xoff, -*yoff); } /* Indexed table */ if (pict->pFormat->index.devPrivate) pixman_image_set_indexed (image, pict->pFormat->index.devPrivate); + /* Add in drawable origin to position within the image */ + *xoff += pict->pDrawable->x; + *yoff += pict->pDrawable->y; + return image; } static void -set_image_properties (pixman_image_t *image, PicturePtr pict) +set_image_properties (pixman_image_t *image, PicturePtr pict, Bool has_clip, int *xoff, int *yoff) { pixman_repeat_t repeat; pixman_filter_t filter; if (pict->transform) { - pixman_image_set_transform ( - image, (pixman_transform_t *)pict->transform); + /* For source images, adjust the transform to account + * for the drawable offset within the pixman image, + * then set the offset to 0 as it will be used + * to compute positions within the transformed image. + */ + if (!has_clip) { + struct pixman_transform adjusted; + + adjusted = *pict->transform; + pixman_transform_translate(&adjusted, + NULL, + pixman_int_to_fixed(*xoff), + pixman_int_to_fixed(*yoff)); + pixman_image_set_transform (image, &adjusted); + *xoff = 0; + *yoff = 0; + } else + pixman_image_set_transform (image, pict->transform); } switch (pict->repeatType) @@ -361,7 +388,8 @@ set_image_properties (pixman_image_t *image, PicturePtr pict) if (pict->alphaMap) { - pixman_image_t *alpha_map = image_from_pict (pict->alphaMap, TRUE, TRUE); + int alpha_xoff, alpha_yoff; + pixman_image_t *alpha_map = image_from_pict_18 (pict->alphaMap, FALSE, &alpha_xoff, &alpha_yoff); pixman_image_set_alpha_map ( image, alpha_map, pict->alphaOrigin.x, pict->alphaOrigin.y); @@ -393,10 +421,9 @@ set_image_properties (pixman_image_t *image, PicturePtr pict) pixman_image_set_source_clipping (image, TRUE); } + pixman_image_t * -image_from_pict (PicturePtr pict, - Bool has_clip, - Bool is_src) +image_from_pict_18 (PicturePtr pict, Bool has_clip, int *xoff, int *yoff) { pixman_image_t *image = NULL; @@ -405,7 +432,7 @@ image_from_pict (PicturePtr pict, if (pict->pDrawable) { - image = create_bits_picture (pict, has_clip); + image = create_bits_picture (pict, has_clip, xoff, yoff); } else if (pict->pSourcePict) { @@ -429,11 +456,18 @@ image_from_pict (PicturePtr pict, } if (image) - set_image_properties (image, pict); + set_image_properties (image, pict, has_clip, xoff, yoff); return image; } +pixman_image_t * +image_from_pict (PicturePtr pict, Bool has_clip, Bool is_src) +{ + int xoff = 0, yoff = 0; + return image_from_pict_18(pict, has_clip, &xoff, &yoff); +} + void free_pixman_pict (PicturePtr pict, pixman_image_t *image) { @@ -463,3 +497,4 @@ fbPictureInit (ScreenPtr pScreen, PictFormatPtr formats, int nformats) return TRUE; } + diff --git a/fb/fbtrap.c b/fb/fbtrap.c index b1e1eff4a..5b5aeaedd 100644 --- a/fb/fbtrap.c +++ b/fb/fbtrap.c @@ -40,7 +40,8 @@ fbAddTraps (PicturePtr pPicture, int ntrap, xTrap *traps) { - pixman_image_t *image = image_from_pict (pPicture, FALSE, FALSE); + int image_xoff, image_yoff; + pixman_image_t *image = image_from_pict_18 (pPicture, FALSE, &image_xoff, &image_yoff); if (!image) return; @@ -56,7 +57,8 @@ fbRasterizeTrapezoid (PicturePtr pPicture, int x_off, int y_off) { - pixman_image_t *image = image_from_pict (pPicture, FALSE, FALSE); + int mask_xoff, mask_yoff; + pixman_image_t *image = image_from_pict_18 (pPicture, FALSE, &mask_xoff, &mask_yoff); if (!image) return; diff --git a/fb/wfbrename.h b/fb/wfbrename.h index 73ee510b9..e9cdca8bb 100644 --- a/fb/wfbrename.h +++ b/fb/wfbrename.h @@ -187,4 +187,5 @@ #define fbZeroSegment wfbZeroSegment #define free_pixman_pict wfb_free_pixman_pict #define image_from_pict wfb_image_from_pict +#define image_from_pict_18 wfb_image_from_pict_18 #define composeFunctions wfbComposeFunctions