summaryrefslogtreecommitdiff
path: root/render/mipict.c
diff options
context:
space:
mode:
Diffstat (limited to 'render/mipict.c')
-rw-r--r--render/mipict.c161
1 files changed, 128 insertions, 33 deletions
diff --git a/render/mipict.c b/render/mipict.c
index ed97acc7b..8e51ebeab 100644
--- a/render/mipict.c
+++ b/render/mipict.c
@@ -249,8 +249,7 @@ miValidatePicture (PicturePtr pPicture,
#define BOUND(v) (INT16) ((v) < MINSHORT ? MINSHORT : (v) > MAXSHORT ? MAXSHORT : (v))
static __inline Bool
-miClipPictureReg (ScreenPtr pScreen,
- RegionPtr pRegion,
+miClipPictureReg (RegionPtr pRegion,
RegionPtr pClip,
int dx,
int dy)
@@ -276,19 +275,22 @@ miClipPictureReg (ScreenPtr pScreen,
REGION_EMPTY(pScreen, pRegion);
}
}
+ else if (!REGION_NOTEMPTY (pScreen, pClip))
+ return FALSE;
else
{
- REGION_TRANSLATE(pScreen, pRegion, dx, dy);
+ if (dx || dy)
+ REGION_TRANSLATE(pScreen, pRegion, -dx, -dy);
if (!REGION_INTERSECT (pScreen, pRegion, pRegion, pClip))
return FALSE;
- REGION_TRANSLATE(pScreen, pRegion, -dx, -dy);
+ if (dx || dy)
+ REGION_TRANSLATE(pScreen, pRegion, dx, dy);
}
- return TRUE;
+ return REGION_NOTEMPTY(pScreen, pRegion);
}
static __inline Bool
-miClipPictureSrc (ScreenPtr pScreen,
- RegionPtr pRegion,
+miClipPictureSrc (RegionPtr pRegion,
PicturePtr pPicture,
int dx,
int dy)
@@ -314,11 +316,70 @@ miClipPictureSrc (ScreenPtr pScreen,
}
else
{
- return miClipPictureReg (pScreen, pRegion, pPicture->pCompositeClip,
- dx, dy);
+ return miClipPictureReg (pRegion,
+ pPicture->pCompositeClip,
+ dx,
+ dy);
+ }
+}
+
+static void
+miCompositeSourceValidate (PicturePtr pPicture,
+ INT16 x,
+ INT16 y,
+ CARD16 width,
+ CARD16 height)
+{
+ DrawablePtr pDrawable = pPicture->pDrawable;
+ ScreenPtr pScreen = pDrawable->pScreen;
+
+ if (pScreen->SourceValidate)
+ {
+ x -= pPicture->pDrawable->x;
+ y -= pPicture->pDrawable->y;
+ if (pPicture->transform)
+ {
+ xPoint points[4];
+ int i;
+ int xmin, ymin, xmax, ymax;
+
+#define VectorSet(i,_x,_y) { points[i].x = _x; points[i].y = _y; }
+ VectorSet (0, x, y);
+ VectorSet (1, x + width, y);
+ VectorSet (2, x, y + height);
+ VectorSet (3, x + width, y + height);
+ xmin = ymin = 32767;
+ xmax = ymax = -32737;
+ for (i = 0; i < 4; i++)
+ {
+ PictVector t;
+ t.vector[0] = IntToxFixed (points[i].x);
+ t.vector[1] = IntToxFixed (points[i].y);
+ t.vector[2] = xFixed1;
+ if (PictureTransformPoint (pPicture->transform, &t))
+ {
+ int tx = xFixedToInt (t.vector[0]);
+ int ty = xFixedToInt (t.vector[1]);
+ if (tx < xmin) xmin = tx;
+ if (tx > xmax) xmax = tx;
+ if (ty < ymin) ymin = ty;
+ if (ty > ymax) ymax = ty;
+ }
+ }
+ x = xmin;
+ y = ymin;
+ width = xmax - xmin;
+ height = ymax - ymin;
+ }
+ (*pScreen->SourceValidate) (pDrawable, x, y, width, height);
}
}
+/*
+ * returns FALSE if the final region is empty. Indistinguishable from
+ * an allocation failure, but rendering ignores those anyways.
+ */
+
Bool
miComputeCompositeRegion (RegionPtr pRegion,
PicturePtr pSrc,
@@ -333,7 +394,6 @@ miComputeCompositeRegion (RegionPtr pRegion,
CARD16 width,
CARD16 height)
{
- ScreenPtr pScreen = pSrc->pDrawable->pScreen;
int v;
pRegion->extents.x1 = xDst;
@@ -347,18 +407,34 @@ miComputeCompositeRegion (RegionPtr pRegion,
if (pRegion->extents.x1 >= pRegion->extents.x2 ||
pRegion->extents.y1 >= pRegion->extents.y2)
{
- REGION_EMPTY (pScreen, pRegion);
- return TRUE;
+ REGION_EMPTY (pDst->pDrawable->pScreen, pRegion);
+ return FALSE;
+ }
+ /* clip against dst */
+ if (!miClipPictureReg (pRegion, pDst->pCompositeClip, 0, 0))
+ {
+ REGION_UNINIT (pScreen, pRegion);
+ return FALSE;
+ }
+ if (pDst->alphaMap)
+ {
+ if (!miClipPictureReg (pRegion, pDst->alphaMap->pCompositeClip,
+ -pDst->alphaOrigin.x,
+ -pDst->alphaOrigin.y))
+ {
+ REGION_UNINIT (pScreen, pRegion);
+ return FALSE;
+ }
}
/* clip against src */
- if (!miClipPictureSrc (pScreen, pRegion, pSrc, xDst - xSrc, yDst - ySrc))
+ if (!miClipPictureSrc (pRegion, pSrc, xDst - xSrc, yDst - ySrc))
{
REGION_UNINIT (pScreen, pRegion);
return FALSE;
}
if (pSrc->alphaMap)
{
- if (!miClipPictureSrc (pScreen, pRegion, pSrc->alphaMap,
+ if (!miClipPictureSrc (pRegion, pSrc->alphaMap,
xDst - (xSrc + pSrc->alphaOrigin.x),
yDst - (ySrc + pSrc->alphaOrigin.y)))
{
@@ -369,15 +445,14 @@ miComputeCompositeRegion (RegionPtr pRegion,
/* clip against mask */
if (pMask)
{
- if (!miClipPictureSrc (pScreen, pRegion, pMask,
- xDst - xMask, yDst - yMask))
+ if (!miClipPictureSrc (pRegion, pMask, xDst - xMask, yDst - yMask))
{
REGION_UNINIT (pScreen, pRegion);
return FALSE;
}
if (pMask->alphaMap)
{
- if (!miClipPictureSrc (pScreen, pRegion, pMask->alphaMap,
+ if (!miClipPictureSrc (pRegion, pMask->alphaMap,
xDst - (xMask + pMask->alphaOrigin.x),
yDst - (yMask + pMask->alphaOrigin.y)))
{
@@ -386,22 +461,9 @@ miComputeCompositeRegion (RegionPtr pRegion,
}
}
}
- if (!miClipPictureReg (pScreen, pRegion, pDst->pCompositeClip, 0, 0))
- {
- REGION_UNINIT (pScreen, pRegion);
- return FALSE;
- }
- if (pDst->alphaMap)
- {
- if (!miClipPictureReg (pScreen,
- pRegion, pDst->alphaMap->pCompositeClip,
- -pDst->alphaOrigin.x,
- -pDst->alphaOrigin.y))
- {
- REGION_UNINIT (pScreen, pRegion);
- return FALSE;
- }
- }
+ miCompositeSourceValidate (pSrc, xSrc, ySrc, width, height);
+ if (pMask)
+ miCompositeSourceValidate (pMask, xMask, yMask, width, height);
return TRUE;
}
@@ -456,6 +518,35 @@ miFillColor (CARD32 pixel, int bits)
return (CARD16) pixel;
}
+Bool
+miIsSolidAlpha (PicturePtr pSrc)
+{
+ ScreenPtr pScreen = pSrc->pDrawable->pScreen;
+ char line[1];
+
+ /* Alpha-only */
+ if (PICT_FORMAT_TYPE (pSrc->format) != PICT_TYPE_A)
+ return FALSE;
+ /* repeat */
+ if (!pSrc->repeat)
+ return FALSE;
+ /* 1x1 */
+ if (pSrc->pDrawable->width != 1 || pSrc->pDrawable->height != 1)
+ return FALSE;
+ line[0] = 1;
+ (*pScreen->GetImage) (pSrc->pDrawable, 0, 0, 1, 1, ZPixmap, ~0L, line);
+ switch (pSrc->pDrawable->bitsPerPixel) {
+ case 1:
+ return (CARD8) line[0] == 1 || (CARD8) line[0] == 0x80;
+ case 4:
+ return (CARD8) line[0] == 0xf || (CARD8) line[0] == 0xf0;
+ case 8:
+ return (CARD8) line[0] == 0xff;
+ default:
+ return FALSE;
+ }
+}
+
void
miRenderPixelToColor (PictFormatPtr format,
CARD32 pixel,
@@ -516,5 +607,9 @@ miPictureInit (ScreenPtr pScreen, PictFormatPtr formats, int nformats)
ps->TriStrip = miTriStrip;
ps->TriFan = miTriFan;
+ ps->RasterizeTrapezoid = 0; /* requires DDX support */
+ ps->AddTraps = 0; /* requires DDX support */
+ ps->AddTriangles = 0; /* requires DDX support */
+
return TRUE;
}