summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/i830.h5
-rw-r--r--src/i830_exa.c55
-rw-r--r--src/i830_render.c118
-rw-r--r--src/i915_render.c10
-rw-r--r--src/i965_render.c42
5 files changed, 143 insertions, 87 deletions
diff --git a/src/i830.h b/src/i830.h
index c84e8023..1319c6a0 100644
--- a/src/i830.h
+++ b/src/i830.h
@@ -524,6 +524,7 @@ typedef struct _I830Rec {
float scale_units[2][2];
/** Transform pointers for src/mask, or NULL if identity */
PictTransform *transform[2];
+ float coord_adjust;
/* i915 EXA render state */
uint32_t mapstate[6];
uint32_t samplerstate[6];
@@ -827,11 +828,11 @@ Bool i965_prepare_composite(int op, PicturePtr pSrc, PicturePtr pMask,
void i965_composite(PixmapPtr pDst, int srcX, int srcY,
int maskX, int maskY, int dstX, int dstY, int w, int h);
-void
+Bool
i830_get_transformed_coordinates(int x, int y, PictTransformPtr transform,
float *x_out, float *y_out);
-void
+Bool
i830_get_transformed_coordinates_3d(int x, int y, PictTransformPtr transform,
float *x_out, float *y_out, float *z_out);
diff --git a/src/i830_exa.c b/src/i830_exa.c
index f9df277e..9b5bb936 100644
--- a/src/i830_exa.c
+++ b/src/i830_exa.c
@@ -339,12 +339,31 @@ I830EXADoneCopy(PixmapPtr pDstPixmap)
#define xFixedToFloat(val) \
((float)xFixedToInt(val) + ((float)xFixedFrac(val) / 65536.0))
+static Bool
+_i830_transform_point (PictTransformPtr transform,
+ float x,
+ float y,
+ float result[3])
+{
+ int j;
+
+ for (j = 0; j < 3; j++)
+ {
+ result[j] = (xFixedToFloat (transform->matrix[j][0]) * x +
+ xFixedToFloat (transform->matrix[j][1]) * y +
+ xFixedToFloat (transform->matrix[j][2]));
+ }
+ if (!result[2])
+ return FALSE;
+ return TRUE;
+}
+
/**
* Returns the floating-point coordinates transformed by the given transform.
*
* transform may be null.
*/
-void
+Bool
i830_get_transformed_coordinates(int x, int y, PictTransformPtr transform,
float *x_out, float *y_out)
{
@@ -352,15 +371,14 @@ i830_get_transformed_coordinates(int x, int y, PictTransformPtr transform,
*x_out = x;
*y_out = y;
} else {
- PictVector v;
-
- v.vector[0] = IntToxFixed(x);
- v.vector[1] = IntToxFixed(y);
- v.vector[2] = xFixed1;
- PictureTransformPoint(transform, &v);
- *x_out = xFixedToFloat(v.vector[0]);
- *y_out = xFixedToFloat(v.vector[1]);
+ float result[3];
+
+ if (!_i830_transform_point (transform, (float) x, (float) y, result))
+ return FALSE;
+ *x_out = result[0] / result[2];
+ *y_out = result[1] / result[2];
}
+ return TRUE;
}
/**
@@ -368,7 +386,7 @@ i830_get_transformed_coordinates(int x, int y, PictTransformPtr transform,
*
* transform may be null.
*/
-void
+Bool
i830_get_transformed_coordinates_3d(int x, int y, PictTransformPtr transform,
float *x_out, float *y_out, float *w_out)
{
@@ -377,16 +395,15 @@ i830_get_transformed_coordinates_3d(int x, int y, PictTransformPtr transform,
*y_out = y;
*w_out = 1;
} else {
- PictVector v;
-
- v.vector[0] = IntToxFixed(x);
- v.vector[1] = IntToxFixed(y);
- v.vector[2] = xFixed1;
- PictureTransformPoint3d(transform, &v);
- *x_out = xFixedToFloat(v.vector[0]);
- *y_out = xFixedToFloat(v.vector[1]);
- *w_out = xFixedToFloat(v.vector[2]);
+ float result[3];
+
+ if (!_i830_transform_point (transform, (float) x, (float) y, result))
+ return FALSE;
+ *x_out = result[0];
+ *y_out = result[1];
+ *w_out = result[2];
}
+ return TRUE;
}
/**
diff --git a/src/i830_render.c b/src/i830_render.c
index 87543ef6..195e9a8c 100644
--- a/src/i830_render.c
+++ b/src/i830_render.c
@@ -396,6 +396,7 @@ i830_prepare_composite(int op, PicturePtr pSrcPicture,
I830Ptr pI830 = I830PTR(pScrn);
uint32_t dst_format, dst_offset, dst_pitch;
Bool is_affine_src, is_affine_mask;
+ Bool is_nearest = FALSE;
IntelEmitInvarientState(pScrn);
*pI830->last_3d = LAST_3D_RENDER;
@@ -407,9 +408,13 @@ i830_prepare_composite(int op, PicturePtr pSrcPicture,
if (!i830_texture_setup(pSrcPicture, pSrc, 0))
I830FALLBACK("fail to setup src texture\n");
+ if (pSrcPicture->filter == PictFilterNearest)
+ is_nearest = TRUE;
if (pMask != NULL) {
if (!i830_texture_setup(pMaskPicture, pMask, 1))
I830FALLBACK("fail to setup mask texture\n");
+ if (pMaskPicture->filter == PictFilterNearest)
+ is_nearest = TRUE;
} else {
pI830->transform[1] = NULL;
pI830->scale_units[1][0] = -1;
@@ -419,6 +424,11 @@ i830_prepare_composite(int op, PicturePtr pSrcPicture,
is_affine_src = i830_transform_is_affine (pI830->transform[0]);
is_affine_mask = i830_transform_is_affine (pI830->transform[1]);
+ if (is_nearest)
+ pI830->coord_adjust = -0.125;
+ else
+ pI830->coord_adjust = 0;
+
if (!is_affine_src || !is_affine_mask)
I830FALLBACK("non-affine transform unsupported on 8xx hardware\n");
@@ -591,56 +601,68 @@ i830_composite(PixmapPtr pDst, int srcX, int srcY, int maskX, int maskY,
per_vertex = 2; /* dest x/y */
if (is_affine_src)
{
- i830_get_transformed_coordinates(srcX, srcY,
- pI830->transform[0],
- &src_x[0], &src_y[0]);
- i830_get_transformed_coordinates(srcX, srcY + h,
- pI830->transform[0],
- &src_x[1], &src_y[1]);
- i830_get_transformed_coordinates(srcX + w, srcY + h,
- pI830->transform[0],
- &src_x[2], &src_y[2]);
+ if (!i830_get_transformed_coordinates(srcX, srcY,
+ pI830->transform[0],
+ &src_x[0], &src_y[0]))
+ return;
+ if (!i830_get_transformed_coordinates(srcX, srcY + h,
+ pI830->transform[0],
+ &src_x[1], &src_y[1]))
+ return;
+ if (!i830_get_transformed_coordinates(srcX + w, srcY + h,
+ pI830->transform[0],
+ &src_x[2], &src_y[2]))
+ return;
per_vertex += 2; /* src x/y */
} else {
- i830_get_transformed_coordinates_3d(srcX, srcY,
- pI830->transform[0],
- &src_x[0], &src_y[0],
- &src_w[0]);
- i830_get_transformed_coordinates_3d(srcX, srcY + h,
- pI830->transform[0],
- &src_x[1], &src_y[1],
- &src_w[1]);
- i830_get_transformed_coordinates_3d(srcX + w, srcY + h,
- pI830->transform[0],
- &src_x[2], &src_y[2],
- &src_w[2]);
+ if (!i830_get_transformed_coordinates_3d(srcX, srcY,
+ pI830->transform[0],
+ &src_x[0], &src_y[0],
+ &src_w[0]))
+ return;
+ if (!i830_get_transformed_coordinates_3d(srcX, srcY + h,
+ pI830->transform[0],
+ &src_x[1], &src_y[1],
+ &src_w[1]))
+ return;
+ if (!i830_get_transformed_coordinates_3d(srcX + w, srcY + h,
+ pI830->transform[0],
+ &src_x[2], &src_y[2],
+ &src_w[2]))
+ return;
per_vertex += 4; /* src x/y/z/w */
}
if (has_mask) {
if (is_affine_mask) {
- i830_get_transformed_coordinates(maskX, maskY,
- pI830->transform[1],
- &mask_x[0], &mask_y[0]);
- i830_get_transformed_coordinates(maskX, maskY + h,
- pI830->transform[1],
- &mask_x[1], &mask_y[1]);
- i830_get_transformed_coordinates(maskX + w, maskY + h,
- pI830->transform[1],
- &mask_x[2], &mask_y[2]);
+ if (!i830_get_transformed_coordinates(maskX, maskY,
+ pI830->transform[1],
+ &mask_x[0], &mask_y[0]))
+ return;
+ if (!i830_get_transformed_coordinates(maskX, maskY + h,
+ pI830->transform[1],
+ &mask_x[1], &mask_y[1]))
+ return;
+ if (!i830_get_transformed_coordinates(maskX + w, maskY + h,
+ pI830->transform[1],
+ &mask_x[2], &mask_y[2]))
+ return;
per_vertex += 2; /* mask x/y */
} else {
- i830_get_transformed_coordinates_3d(maskX, maskY,
- pI830->transform[1],
- &mask_x[0], &mask_y[0],
- &mask_w[0]);
- i830_get_transformed_coordinates_3d(maskX, maskY + h,
- pI830->transform[1],
- &mask_x[1], &mask_y[1],
- &mask_w[1]);
- i830_get_transformed_coordinates_3d(maskX + w, maskY + h,
- pI830->transform[1],
- &mask_x[2], &mask_y[2],
- &mask_w[2]);
+ if (!i830_get_transformed_coordinates_3d(maskX, maskY,
+ pI830->transform[1],
+ &mask_x[0], &mask_y[0],
+ &mask_w[0]))
+ return;
+ if (!i830_get_transformed_coordinates_3d(maskX, maskY + h,
+ pI830->transform[1],
+ &mask_x[1], &mask_y[1],
+ &mask_w[1]))
+ return;
+ if (!i830_get_transformed_coordinates_3d(maskX + w, maskY + h,
+ pI830->transform[1],
+ &mask_x[2], &mask_y[2],
+ &mask_w[2]))
+ return;
per_vertex += 4; /* mask x/y/z/w */
}
}
@@ -655,8 +677,8 @@ i830_composite(PixmapPtr pDst, int srcX, int srcY, int maskX, int maskY,
OUT_BATCH(MI_NOOP);
OUT_BATCH(PRIM3D_INLINE | PRIM3D_RECTLIST | (num_floats-1));
- OUT_BATCH_F(-0.125 + dstX + w);
- OUT_BATCH_F(-0.125 + dstY + h);
+ OUT_BATCH_F(pI830->coord_adjust + dstX + w);
+ OUT_BATCH_F(pI830->coord_adjust + dstY + h);
OUT_BATCH_F(src_x[2] / pI830->scale_units[0][0]);
OUT_BATCH_F(src_y[2] / pI830->scale_units[0][1]);
if (!is_affine_src) {
@@ -672,8 +694,8 @@ i830_composite(PixmapPtr pDst, int srcX, int srcY, int maskX, int maskY,
}
}
- OUT_BATCH_F(-0.125 + dstX);
- OUT_BATCH_F(-0.125 + dstY + h);
+ OUT_BATCH_F(pI830->coord_adjust + dstX);
+ OUT_BATCH_F(pI830->coord_adjust + dstY + h);
OUT_BATCH_F(src_x[1] / pI830->scale_units[0][0]);
OUT_BATCH_F(src_y[1] / pI830->scale_units[0][1]);
if (!is_affine_src) {
@@ -689,8 +711,8 @@ i830_composite(PixmapPtr pDst, int srcX, int srcY, int maskX, int maskY,
}
}
- OUT_BATCH_F(-0.125 + dstX);
- OUT_BATCH_F(-0.125 + dstY);
+ OUT_BATCH_F(pI830->coord_adjust + dstX);
+ OUT_BATCH_F(pI830->coord_adjust + dstY);
OUT_BATCH_F(src_x[0] / pI830->scale_units[0][0]);
OUT_BATCH_F(src_y[0] / pI830->scale_units[0][1]);
if (!is_affine_src) {
diff --git a/src/i915_render.c b/src/i915_render.c
index 9c6da095..2b9ed04e 100644
--- a/src/i915_render.c
+++ b/src/i915_render.c
@@ -321,6 +321,7 @@ i915_prepare_composite(int op, PicturePtr pSrcPicture,
int out_reg = FS_OC;
FS_LOCALS(20);
Bool is_affine_src, is_affine_mask;
+ Bool is_nearest = FALSE;
IntelEmitInvarientState(pScrn);
*pI830->last_3d = LAST_3D_RENDER;
@@ -332,9 +333,13 @@ i915_prepare_composite(int op, PicturePtr pSrcPicture,
if (!i915_texture_setup(pSrcPicture, pSrc, 0))
I830FALLBACK("fail to setup src texture\n");
+ if (pSrcPicture->filter == PictFilterNearest)
+ is_nearest = TRUE;
if (pMask != NULL) {
if (!i915_texture_setup(pMaskPicture, pMask, 1))
I830FALLBACK("fail to setup mask texture\n");
+ if (pMaskPicture->filter == PictFilterNearest)
+ is_nearest = TRUE;
} else {
pI830->transform[1] = NULL;
pI830->scale_units[1][0] = -1;
@@ -343,6 +348,11 @@ i915_prepare_composite(int op, PicturePtr pSrcPicture,
is_affine_src = i830_transform_is_affine (pI830->transform[0]);
is_affine_mask = i830_transform_is_affine (pI830->transform[1]);
+ if (is_nearest)
+ pI830->coord_adjust = -0.125;
+ else
+ pI830->coord_adjust = 0;
+
if (pMask == NULL) {
BEGIN_BATCH(10);
OUT_BATCH(_3DSTATE_MAP_STATE | 3);
diff --git a/src/i965_render.c b/src/i965_render.c
index ada3919a..93583b0a 100644
--- a/src/i965_render.c
+++ b/src/i965_render.c
@@ -1093,29 +1093,35 @@ i965_composite(PixmapPtr pDst, int srcX, int srcY, int maskX, int maskY,
float src_x[3], src_y[3], mask_x[3], mask_y[3];
int i;
- i830_get_transformed_coordinates(srcX, srcY,
- pI830->transform[0],
- &src_x[0], &src_y[0]);
- i830_get_transformed_coordinates(srcX, srcY + h,
- pI830->transform[0],
- &src_x[1], &src_y[1]);
- i830_get_transformed_coordinates(srcX + w, srcY + h,
- pI830->transform[0],
- &src_x[2], &src_y[2]);
+ if (!i830_get_transformed_coordinates(srcX, srcY,
+ pI830->transform[0],
+ &src_x[0], &src_y[0]))
+ return;
+ if (!i830_get_transformed_coordinates(srcX, srcY + h,
+ pI830->transform[0],
+ &src_x[1], &src_y[1]))
+ return;
+ if (!i830_get_transformed_coordinates(srcX + w, srcY + h,
+ pI830->transform[0],
+ &src_x[2], &src_y[2]))
+ return;
if (pI830->scale_units[1][0] == -1 || pI830->scale_units[1][1] == -1) {
has_mask = FALSE;
} else {
has_mask = TRUE;
- i830_get_transformed_coordinates(maskX, maskY,
- pI830->transform[1],
- &mask_x[0], &mask_y[0]);
- i830_get_transformed_coordinates(maskX, maskY + h,
- pI830->transform[1],
- &mask_x[1], &mask_y[1]);
- i830_get_transformed_coordinates(maskX + w, maskY + h,
- pI830->transform[1],
- &mask_x[2], &mask_y[2]);
+ if (!i830_get_transformed_coordinates(maskX, maskY,
+ pI830->transform[1],
+ &mask_x[0], &mask_y[0]))
+ return;
+ if (!i830_get_transformed_coordinates(maskX, maskY + h,
+ pI830->transform[1],
+ &mask_x[1], &mask_y[1]))
+ return;
+ if (!i830_get_transformed_coordinates(maskX + w, maskY + h,
+ pI830->transform[1],
+ &mask_x[2], &mask_y[2]))
+ return;
}
/* Wait for any existing composite rectangles to land before we overwrite