aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--src/libclut.h60
-rw-r--r--src/test.c96
2 files changed, 113 insertions, 43 deletions
diff --git a/src/libclut.h b/src/libclut.h
index 0d63d4a..d355d13 100644
--- a/src/libclut.h
+++ b/src/libclut.h
@@ -45,9 +45,9 @@
#define libclut_rgb_contrast(clut, max, type, r, g, b) \
do \
{ \
- if ((r) != 1.0) libclut__(clut, red, type, LIBCLUT_VALUE - (max) * 0.5 * (r) + (max) * 0.5); \
- if ((g) != 1.0) libclut__(clut, green, type, LIBCLUT_VALUE - (max) * 0.5 * (g) + (max) * 0.5); \
- if ((b) != 1.0) libclut__(clut, blue, type, LIBCLUT_VALUE - (max) * 0.5 * (b) + (max) * 0.5); \
+ if ((r) != 1.0) libclut__(clut, red, type, (LIBCLUT_VALUE - (max) * 0.5) * (r) + (max) * 0.5); \
+ if ((g) != 1.0) libclut__(clut, green, type, (LIBCLUT_VALUE - (max) * 0.5) * (g) + (max) * 0.5); \
+ if ((b) != 1.0) libclut__(clut, blue, type, (LIBCLUT_VALUE - (max) * 0.5) * (b) + (max) * 0.5); \
} \
while (0)
@@ -346,15 +346,15 @@
double m__ = (double)(max); \
size_t i__; \
if (rp) \
- for (i__ = 0; i++ < (clut)->red_size; i__++) \
+ for (i__ = 0; i__ < (clut)->red_size; i__++) \
if ((clut)->red[i__] && ((clut)->red[i__] != (max))) \
(clut)->red[i__] = (type)(m__ * (0.5 - log(m__ / (clut)->red[i__] - 1.0) / r__)); \
if (gp) \
- for (i__ = 0; i++ < (clut)->green_size; i__++) \
+ for (i__ = 0; i__ < (clut)->green_size; i__++) \
if ((clut)->green[i__] && ((clut)->green[i__] != (max))) \
(clut)->green[i__] = (type)(m__ * (0.5 - log(m__ / (clut)->green[i__] - 1.0) / g__)); \
if (bp) \
- for (i__ = 0; i++ < (clut)->blue_size; i__++) \
+ for (i__ = 0; i__ < (clut)->blue_size; i__++) \
if ((clut)->blue[i__] && ((clut)->blue[i__] != (max))) \
(clut)->blue[i__] = (type)(m__ * (0.5 - log(m__ / (clut)->blue[i__] - 1.0) / b__)); \
} \
@@ -621,31 +621,29 @@
*/
#define libclut_lower_resolution__(clut, channel, max, type, x, y) \
do \
- { \
- if ((x) || (y)) \
- { \
- size_t x__, y__, i__, n__ = (clut)->channel##_size; \
- double xm__ = (double)((x) - 1), ym__ = (double)((y) - 1); \
- double m__ = (double)(max); \
- type c__[n__]; /* Do not use alloca! */ \
- for (i__ = 0; i__ < n__; i__++) \
- { \
- if ((x__ = i__), (x)) \
- { \
- x__ = (size_t)((double)i__ * (x) / n__); \
- x__ = (size_t)((double)x__ * i__ / xm__); \
- } \
- if (!(y)) \
- c__[i__] = (clut)->channel[x__]; \
- else \
- { \
- y__ = (size_t)((double)((clut)->channel[x__]) / (max) * ym__ + 0.5); \
- c__[i__] = (type)((double)y__ / ym__ * m__); \
- } \
- } \
- memcpy((clut)->channel, c__, n__ * sizeof(type)); \
- } \
- } \
+ if ((x) || (y)) \
+ { \
+ size_t x__, y__, i__, n__ = (clut)->channel##_size; \
+ double xm__ = (double)((x) - 1), ym__ = (double)((y) - 1); \
+ double m__ = (double)(max), nm__ = (double)(n__ - 1); \
+ type c__[n__]; /* Do not use alloca! */ \
+ for (i__ = 0; i__ < n__; i__++) \
+ { \
+ if ((x__ = i__), (x)) \
+ { \
+ x__ = (size_t)((double)i__ * (x) / n__); \
+ x__ = (size_t)((double)x__ * nm__ / xm__); \
+ } \
+ if (!(y)) \
+ c__[i__] = (clut)->channel[x__]; \
+ else \
+ { \
+ y__ = (size_t)((double)((clut)->channel[x__]) / (max) * ym__ + 0.5); \
+ c__[i__] = (type)((double)y__ / ym__ * m__); \
+ } \
+ } \
+ memcpy((clut)->channel, c__, n__ * sizeof(type)); \
+ } \
while (0)
diff --git a/src/test.c b/src/test.c
index 393e11e..2d9b1a5 100644
--- a/src/test.c
+++ b/src/test.c
@@ -22,6 +22,8 @@
#include <stdlib.h>
#include <string.h>
+#include <math.h>
+
struct clut
@@ -36,9 +38,23 @@ struct clut
-static inline int clutcmp(const struct clut *a, const struct clut *b)
+static inline int clutcmp(const struct clut *a, const struct clut *b, uint16_t tol)
{
- return memcmp(a->red, b->red, 3 * 256 * sizeof(uint16_t));
+ size_t i;
+ if (tol == 0)
+ return memcmp(a->red, b->red, 3 * 256 * sizeof(uint16_t));
+ for (i = 0; i < 3 * 256; i++)
+ if (a->red[i] > b->red[i])
+ {
+ if (a->red[i] - b->red[i] > tol)
+ return +1;
+ }
+ else if (a->red[i] < b->red[i])
+ {
+ if (b->red[i] - a->red[i] > tol)
+ return -1;
+ }
+ return 0;
}
@@ -50,6 +66,7 @@ static int dumpcluts(const struct clut *a, const struct clut *b)
i, i, a->red[i], b->red[i], a->green[i], b->green[i], a->blue[i], b->blue[i]);
}
+
static double make_double(double x)
{
return x * 2;
@@ -68,6 +85,7 @@ int main(int argc, char *argv[])
struct clut t1, t2, t3;
size_t i, j;
int rc = 0;
+ double param;
t1. red_size = t2. red_size = t3. red_size = 256;
t1.green_size = t2.green_size = t3.green_size = 256;
@@ -83,7 +101,7 @@ int main(int argc, char *argv[])
libclut_start_over(&t1, UINT16_MAX, uint16_t, 1, 1, 1);
for (i = 0; i < 256; i++)
t2.blue[i] = t2.green[i] = t2.red[i] = (uint16_t)((i << 8) | i);
- if (clutcmp(&t1, &t2))
+ if (clutcmp(&t1, &t2, 0))
printf("libclut_start_over failed\n"), rc = 1;
@@ -93,7 +111,7 @@ int main(int argc, char *argv[])
t2.blue[j] = t2.green[j] = t2.red[j] = (uint16_t)i;
}
libclut_negative(&t1, UINT16_MAX, uint16_t, 1, 1, 1);
- if (clutcmp(&t1, &t2))
+ if (clutcmp(&t1, &t2, 0))
printf("libclut_negative failed\n"), rc = 1;
@@ -103,7 +121,7 @@ int main(int argc, char *argv[])
t2.blue[i] = t2.green[i] = t2.red[i] = UINT16_MAX - (uint16_t)i;
}
libclut_rgb_invert(&t1, UINT16_MAX, uint16_t, 1, 1, 1);
- if (clutcmp(&t1, &t2))
+ if (clutcmp(&t1, &t2, 0))
printf("libclut_rgb_invert failed\n"), rc = 1;
@@ -113,7 +131,7 @@ int main(int argc, char *argv[])
t2.blue[i] = 1 + (t2.green[i] = 1 + (t2.red[i] = 1000 + (uint16_t)i));
}
libclut_rgb_limits(&t1, UINT16_MAX, uint16_t, 1000, 1255, 1001, 1256, 1002, 1257);
- if (clutcmp(&t1, &t2))
+ if (clutcmp(&t1, &t2, 0))
printf("libclut_rgb_limits failed\n"), rc = 1;
@@ -125,7 +143,7 @@ int main(int argc, char *argv[])
t2.blue[i] = t1.blue[i] * 4;
}
libclut_rgb_brightness(&t1, UINT16_MAX, uint16_t, 2, 3, 4);
- if (clutcmp(&t1, &t2))
+ if (clutcmp(&t1, &t2, 0))
printf("libclut_rgb_brightness failed\n"), rc = 1;
@@ -135,9 +153,67 @@ int main(int argc, char *argv[])
t2.blue[i] = t2.green[i] = 2 * (t2.red[i] = (uint16_t)i);
}
libclut_manipulate(&t1, UINT16_MAX, uint16_t, (double (*)(double))(NULL), make_double, make_double);
- if (clutcmp(&t1, &t2))
+ if (clutcmp(&t1, &t2, 0))
printf("libclut_manipulate failed\n"), rc = 1;
+
+ for (i = 0; i < 256; i++)
+ {
+ t1.blue[i] = t1.green[i] = t1.red[i] = (uint16_t)i;
+ t2.blue[i] = t2.green[i] = t2.red[i] = (uint16_t)(pow((double)i / UINT16_MAX, 1.0 / 1.1) * UINT16_MAX);
+ }
+ libclut_gamma(&t1, UINT16_MAX, uint16_t, 1.1, 1.1, 1.1);
+ if (clutcmp(&t1, &t2, 0))
+ printf("libclut_gamma failed\n"), rc = 1;
+
+
+ for (i = 0; i < 256; i++)
+ {
+ t1.blue[i] = t1.green[i] = t1.red[i] = (uint16_t)((i << 8) | i);
+ t2.blue[i] = t2.green[i] = t2.red[i] = (t1.red[i] - UINT16_MAX / 2) / 2 + UINT16_MAX / 2;
+ }
+ libclut_rgb_contrast(&t1, UINT16_MAX, uint16_t, 0.5, 0.5, 0.5);
+ if (clutcmp(&t1, &t2, 1))
+ printf("libclut_rgb_contrast failed\n"), rc = 1;
+
+
+ param = 2.0;
+ for (i = 0; i < 256; i++)
+ {
+ double x = i / 255.0;
+ if (i % 255)
+ {
+ x = 1.0 / x - 1.0;
+ x = log(x);
+ x = 0.5 - x / param;
+ }
+ t1.blue[i] = t1.green[i] = t1.red[i] = (uint16_t)((i << 8) | i);
+ t2.blue[i] = t2.green[i] = t2.red[i] = (uint16_t)(x * UINT16_MAX);
+ }
+ libclut_sigmoid(&t1, UINT16_MAX, uint16_t, &param, &param, &param);
+ if (clutcmp(&t1, &t2, 0))
+ printf("libclut_sigmoid failed\n"), rc = 1;
+
+
+ for (i = 0; i < 256; i++)
+ {
+ t1.blue[i] = t1.green[i] = t1.red[i] = (uint16_t)((i << 8) | i);
+ t2.blue[i] = t2.green[i] = t2.red[i] = t1.red[i & ~15] | (t1.red[i & ~15] >> 4);
+ }
+ libclut_lower_resolution(&t1, UINT16_MAX, uint16_t, 16, 0, 16, 0, 16, 0);
+ if (clutcmp(&t1, &t2, 0))
+ printf("libclut_lower_resolution (x) failed\n"), rc = 1;
+
+
+ for (i = 0; i < 256; i++)
+ {
+ t1.blue[i] = t1.green[i] = t1.red[i] = (uint16_t)((i << 8) | i);
+ t2.blue[i] = t2.green[i] = t2.red[i] = (uint16_t)(i / 255.0 * 15.0 + 0.5) * UINT16_MAX / 15;
+ }
+ libclut_lower_resolution(&t1, UINT16_MAX, uint16_t, 0, 16, 0, 16, 0, 16);
+ if (clutcmp(&t1, &t2, 0))
+ printf("libclut_lower_resolution (y) failed\n"), rc = 1;
+
if (!rc)
printf("everything is fine\n");
@@ -150,18 +226,14 @@ int main(int argc, char *argv[])
/*
- libclut_rgb_contrast
libclut_cie_contrast
libclut_cie_brightness
libclut_linearise
libclut_standardise
- libclut_gamma
libclut_cie_invert
- libclut_sigmoid
libclut_cie_limits
libclut_cie_manipulate
libclut_clip
- libclut_lower_resolution
libclut_apply
libclut_cie_apply
*/