[cairo-commit] 2 commits - test/buffer-diff.c test/buffer-diff.h
test/pdiff test/xlib-surface.c
Carl Worth
cworth at kemper.freedesktop.org
Tue Dec 12 04:22:12 PST 2006
test/buffer-diff.c | 103 +++++++++++++++++++++++++++++----------------
test/buffer-diff.h | 8 ---
test/pdiff/Metric.cpp | 112 ++++++++++++++++++++++++++++++++------------------
test/xlib-surface.c | 4 -
4 files changed, 139 insertions(+), 88 deletions(-)
New commits:
diff-tree 41e01d95edd7eb573a8b79acd0ab2b9de8cdab40 (from b50b8db6d7d3d0a887ee18ad5e8e0455ed794429)
Author: Carl Worth <cworth at cworth.org>
Date: Tue Dec 12 03:13:38 2006 -0800
pdiff: Factor out a comparison function that doesn't read the 'args' structure
This is one small step in "libifying" pdiff which will make it
easier to share this code inside cairo's test suite.
diff --git a/test/pdiff/Metric.cpp b/test/pdiff/Metric.cpp
index 58d67c7..7974fa5 100644
--- a/test/pdiff/Metric.cpp
+++ b/test/pdiff/Metric.cpp
@@ -122,6 +122,13 @@ void XYZToLAB(float x, float y, float z,
B = 200.0f * (f[1] - f[2]);
}
+int Yee_Compare_Images(RGBAImage *image_a,
+ RGBAImage *image_b,
+ float gamma,
+ float luminance,
+ float field_of_view,
+ bool verbose);
+
bool Yee_Compare(CompareArgs &args)
{
if ((args.ImgA->Get_Width() != args.ImgB->Get_Width()) ||
@@ -130,7 +137,7 @@ bool Yee_Compare(CompareArgs &args)
return false;
}
- unsigned int i, dim;
+ unsigned int i, dim, pixels_failed;
dim = args.ImgA->Get_Width() * args.ImgA->Get_Height();
bool identical = true;
for (i = 0; i < dim; i++) {
@@ -143,7 +150,49 @@ bool Yee_Compare(CompareArgs &args)
args.ErrorStr = "Images are binary identical\n";
return true;
}
+
+ pixels_failed = Yee_Compare_Images (args.ImgA, args.ImgB,
+ args.Gamma, args.Luminance,
+ args.FieldOfView, args.Verbose);
+
+ if (pixels_failed < args.ThresholdPixels) {
+ args.ErrorStr = "Images are perceptually indistinguishable\n";
+ return true;
+ }
+ char different[100];
+ sprintf(different, "%d pixels are different\n", pixels_failed);
+
+ args.ErrorStr = "Images are visibly different\n";
+ args.ErrorStr += different;
+
+ if (args.ImgDiff) {
+#if IMAGE_DIFF_CODE_ENABLED
+ if (args.ImgDiff->WritePPM()) {
+ args.ErrorStr += "Wrote difference image to ";
+ args.ErrorStr+= args.ImgDiff->Get_Name();
+ args.ErrorStr += "\n";
+ } else {
+ args.ErrorStr += "Could not write difference image to ";
+ args.ErrorStr+= args.ImgDiff->Get_Name();
+ args.ErrorStr += "\n";
+ }
+#endif
+ args.ErrorStr += "Generation of image \"difference\" is currently disabled\n";
+ }
+ return false;
+}
+
+int Yee_Compare_Images(RGBAImage *image_a,
+ RGBAImage *image_b,
+ float gamma,
+ float luminance,
+ float field_of_view,
+ bool verbose)
+{
+ unsigned int i, dim;
+ dim = image_a->Get_Width() * image_a->Get_Height();
+
// assuming colorspaces are in Adobe RGB (1998) convert to XYZ
float *aX = new float[dim];
float *aY = new float[dim];
@@ -159,39 +208,41 @@ bool Yee_Compare(CompareArgs &args)
float *aB = new float[dim];
float *bB = new float[dim];
- if (args.Verbose) printf("Converting RGB to XYZ\n");
+ if (verbose) printf("Converting RGB to XYZ\n");
unsigned int x, y, w, h;
- w = args.ImgA->Get_Width();
- h = args.ImgA->Get_Height();
+ w = image_a->Get_Width();
+ h = image_a->Get_Height();
for (y = 0; y < h; y++) {
for (x = 0; x < w; x++) {
float r, g, b, l;
i = x + y * w;
- r = powf(args.ImgA->Get_Red(i) / 255.0f, args.Gamma);
- g = powf(args.ImgA->Get_Green(i) / 255.0f, args.Gamma);
- b = powf(args.ImgA->Get_Blue(i) / 255.0f, args.Gamma);
- AdobeRGBToXYZ(r,g,b,aX[i],aY[i],aZ[i]);
+ r = powf(image_a->Get_Red(i) / 255.0f, gamma);
+ g = powf(image_a->Get_Green(i) / 255.0f, gamma);
+ b = powf(image_a->Get_Blue(i) / 255.0f, gamma);
+
+ AdobeRGBToXYZ(r,g,b,aX[i],aY[i],aZ[i]);
XYZToLAB(aX[i], aY[i], aZ[i], l, aA[i], aB[i]);
- r = powf(args.ImgB->Get_Red(i) / 255.0f, args.Gamma);
- g = powf(args.ImgB->Get_Green(i) / 255.0f, args.Gamma);
- b = powf(args.ImgB->Get_Blue(i) / 255.0f, args.Gamma);
+ r = powf(image_b->Get_Red(i) / 255.0f, gamma);
+ g = powf(image_b->Get_Green(i) / 255.0f, gamma);
+ b = powf(image_b->Get_Blue(i) / 255.0f, gamma);
+
AdobeRGBToXYZ(r,g,b,bX[i],bY[i],bZ[i]);
XYZToLAB(bX[i], bY[i], bZ[i], l, bA[i], bB[i]);
- aLum[i] = aY[i] * args.Luminance;
- bLum[i] = bY[i] * args.Luminance;
+ aLum[i] = aY[i] * luminance;
+ bLum[i] = bY[i] * luminance;
}
}
- if (args.Verbose) printf("Constructing Laplacian Pyramids\n");
+ if (verbose) printf("Constructing Laplacian Pyramids\n");
LPyramid *la = new LPyramid(aLum, w, h);
LPyramid *lb = new LPyramid(bLum, w, h);
- float num_one_degree_pixels = (float) (2 * tan( args.FieldOfView * 0.5 * M_PI / 180) * 180 / M_PI);
+ float num_one_degree_pixels = (float) (2 * tan(field_of_view * 0.5 * M_PI / 180) * 180 / M_PI);
float pixels_per_degree = w / num_one_degree_pixels;
- if (args.Verbose) printf("Performing test\n");
+ if (verbose) printf("Performing test\n");
float num_pixels = 1;
unsigned int adaptation_level = 0;
@@ -262,8 +313,10 @@ bool Yee_Compare(CompareArgs &args)
pass = false;
}
}
- if (!pass) {
+ if (!pass)
pixels_failed++;
+#if IMAGE_DIFF_ENABLED
+ if (!pass) {
if (args.ImgDiff) {
args.ImgDiff->Set(255, 0, 0, 255, index);
}
@@ -272,6 +325,7 @@ bool Yee_Compare(CompareArgs &args)
args.ImgDiff->Set(0, 0, 0, 255, index);
}
}
+#endif
}
}
@@ -289,28 +343,6 @@ bool Yee_Compare(CompareArgs &args)
if (bA) delete bA;
if (aB) delete aB;
if (bB) delete bB;
-
- if (pixels_failed < args.ThresholdPixels) {
- args.ErrorStr = "Images are perceptually indistinguishable\n";
- return true;
- }
-
- char different[100];
- sprintf(different, "%d pixels are different\n", pixels_failed);
- args.ErrorStr = "Images are visibly different\n";
- args.ErrorStr += different;
-
- if (args.ImgDiff) {
- if (args.ImgDiff->WritePPM()) {
- args.ErrorStr += "Wrote difference image to ";
- args.ErrorStr+= args.ImgDiff->Get_Name();
- args.ErrorStr += "\n";
- } else {
- args.ErrorStr += "Could not write difference image to ";
- args.ErrorStr+= args.ImgDiff->Get_Name();
- args.ErrorStr += "\n";
- }
- }
- return false;
+ return pixels_failed;
}
diff-tree b50b8db6d7d3d0a887ee18ad5e8e0455ed794429 (from 1781e6018c17909311295a9cc74b70500c6b4d0a)
Author: Carl Worth <cworth at cworth.org>
Date: Tue Dec 12 02:17:19 2006 -0800
test: Simplify buffer_diff by handling device offset in advance
In a manner similar to flattening in advance, we now extract the sub-
surface of interest (when testing with device offsets) before calling
into the buffer_diff functions. This allows these functions to accept
a single stride value once again instead of one for each of the three
images.
diff --git a/test/buffer-diff.c b/test/buffer-diff.c
index 1a51ea9..819ba16 100644
--- a/test/buffer-diff.c
+++ b/test/buffer-diff.c
@@ -64,9 +64,7 @@ buffer_diff_core (unsigned char *_buf_a,
unsigned char *_buf_diff,
int width,
int height,
- int stride_a,
- int stride_b,
- int stride_diff,
+ int stride,
pixman_bits_t mask,
buffer_diff_result_t *result_ret)
{
@@ -77,14 +75,12 @@ buffer_diff_core (unsigned char *_buf_a,
pixman_bits_t *buf_b = (pixman_bits_t*)_buf_b;
pixman_bits_t *buf_diff = (pixman_bits_t*)_buf_diff;
- stride_a /= sizeof(pixman_bits_t);
- stride_b /= sizeof(pixman_bits_t);
- stride_diff /= sizeof(pixman_bits_t);
+ stride /= sizeof(pixman_bits_t);
for (y = 0; y < height; y++)
{
- row_a = buf_a + y * stride_a;
- row_b = buf_b + y * stride_b;
- row = buf_diff + y * stride_diff;
+ row_a = buf_a + y * stride;
+ row_b = buf_b + y * stride;
+ row = buf_diff + y * stride;
for (x = 0; x < width; x++)
{
/* check if the pixels are the same */
@@ -126,13 +122,11 @@ buffer_diff (unsigned char *buf_a,
unsigned char *buf_diff,
int width,
int height,
- int stride_a,
- int stride_b,
- int stride_diff,
+ int stride,
buffer_diff_result_t *result)
{
buffer_diff_core(buf_a, buf_b, buf_diff,
- width, height, stride_a, stride_b, stride_diff, 0xffffffff,
+ width, height, stride, 0xffffffff,
result);
}
@@ -142,13 +136,11 @@ buffer_diff_noalpha (unsigned char *buf_
unsigned char *buf_diff,
int width,
int height,
- int stride_a,
- int stride_b,
- int stride_diff,
+ int stride,
buffer_diff_result_t *result)
{
buffer_diff_core(buf_a, buf_b, buf_diff,
- width, height, stride_a, stride_b, stride_diff, 0x00ffffff,
+ width, height, stride, 0x00ffffff,
result);
}
@@ -195,6 +187,35 @@ flatten_surface (cairo_surface_t **surfa
*surface = flat;
}
+/* Given an image surface, create a new surface that has the same
+ * contents as the sub-surface with its origin at x,y.
+ *
+ * The original surface will be destroyed.
+ */
+static void
+extract_sub_surface (cairo_surface_t **surface, int x, int y)
+{
+ cairo_surface_t *sub;
+ cairo_t *cr;
+
+ sub = cairo_image_surface_create (CAIRO_FORMAT_ARGB32,
+ cairo_image_surface_get_width (*surface) - x,
+ cairo_image_surface_get_height (*surface) - y);
+
+ /* We don't use a device offset like flatten_surface. That's not
+ * for any important reason, (the results should be
+ * identical). This style just seemed more natural to me this
+ * time, so I'm leaving both here so I can look at both to see
+ * which I like better. */
+ cr = cairo_create (sub);
+ cairo_set_source_surface (cr, *surface, -x, -y);
+ cairo_set_operator (cr, CAIRO_OPERATOR_SOURCE);
+ cairo_paint (cr);
+
+ cairo_surface_destroy (*surface);
+ *surface = sub;
+}
+
/* Image comparison code courtesy of Richard Worth <richard at theworths.org>
* Returns number of pixels changed, (or -1 on error).
* Also saves a "diff" image intended to visually show where the
@@ -243,13 +264,32 @@ image_diff_core (const char *filename_a,
return status;
}
- width_a = cairo_image_surface_get_width (surface_a) - ax;
- height_a = cairo_image_surface_get_height (surface_a) - ay;
- width_b = cairo_image_surface_get_width (surface_b) - bx;
- height_b = cairo_image_surface_get_height (surface_b) - by;
+ if (flatten) {
+ flatten_surface (&surface_a, ax, ay);
+ flatten_surface (&surface_b, bx, by);
+ ax = ay = bx = by = 0;
+ }
+
+ if (ax || ay) {
+ extract_sub_surface (&surface_a, ax, ay);
+ ax = ay = 0;
+ }
+
+ if (bx || by) {
+ extract_sub_surface (&surface_b, bx, by);
+ bx = by = 0;
+ }
+
+ width_a = cairo_image_surface_get_width (surface_a);
+ height_a = cairo_image_surface_get_height (surface_a);
+ stride_a = cairo_image_surface_get_stride (surface_a);
+ width_b = cairo_image_surface_get_width (surface_b);
+ height_b = cairo_image_surface_get_height (surface_b);
+ stride_b = cairo_image_surface_get_stride (surface_b);
if (width_a != width_b ||
- height_a != height_b)
+ height_a != height_b ||
+ stride_a != stride_b)
{
cairo_test_log ("Error: Image size mismatch: (%dx%d) vs. (%dx%d)\n"
" for %s vs. %s\n",
@@ -261,26 +301,13 @@ image_diff_core (const char *filename_a,
return CAIRO_STATUS_SURFACE_TYPE_MISMATCH;
}
- if (flatten) {
- flatten_surface (&surface_a, ax, ay);
- flatten_surface (&surface_b, bx, by);
- ax = ay = bx = by = 0;
- }
-
surface_diff = cairo_image_surface_create (CAIRO_FORMAT_ARGB32,
width_a, height_a);
- stride_a = cairo_image_surface_get_stride (surface_a);
- stride_b = cairo_image_surface_get_stride (surface_b);
-
- buffer_diff (cairo_image_surface_get_data (surface_a)
- + (ay * stride_a) + ax * 4,
- cairo_image_surface_get_data (surface_b)
- + (by * stride_b) + by * 4,
+ buffer_diff (cairo_image_surface_get_data (surface_a),
+ cairo_image_surface_get_data (surface_b),
cairo_image_surface_get_data (surface_diff),
- width_a, height_a,
- stride_a, stride_b,
- cairo_image_surface_get_stride (surface_diff),
+ width_a, height_a, stride_a,
result);
if (result->pixels_changed) {
diff --git a/test/buffer-diff.h b/test/buffer-diff.h
index bef42cf..d95c213 100644
--- a/test/buffer-diff.h
+++ b/test/buffer-diff.h
@@ -50,9 +50,7 @@ buffer_diff (unsigned char *buf_a,
unsigned char *buf_diff,
int width,
int height,
- int stride_a,
- int stride_b,
- int stride_diff,
+ int stride,
buffer_diff_result_t *result);
/* Compares two image buffers ignoring the alpha channel.
@@ -69,9 +67,7 @@ buffer_diff_noalpha (unsigned char *buf_
unsigned char *buf_diff,
int width,
int height,
- int stride_a,
- int stride_b,
- int stride_diff,
+ int stride,
buffer_diff_result_t *result);
/* Compares two image buffers ignoring the alpha channel. A return
diff --git a/test/xlib-surface.c b/test/xlib-surface.c
index ccde14c..44bea92 100644
--- a/test/xlib-surface.c
+++ b/test/xlib-surface.c
@@ -166,8 +166,6 @@ do_test (Display *dpy,
SIZE - OFFSCREEN_OFFSET,
SIZE - OFFSCREEN_OFFSET,
4 * SIZE,
- 4 * SIZE,
- 4 * SIZE,
&result);
} else {
buffer_diff_noalpha (reference_data,
@@ -176,8 +174,6 @@ do_test (Display *dpy,
SIZE,
SIZE,
4 * SIZE,
- 4 * SIZE,
- 4 * SIZE,
&result);
}
More information about the cairo-commit
mailing list