changeset 36114:2c96438ef2ad

Avoid 3D texture with border. It doesn't really improve quality and it is badly supported, for example with ATI HD5000 cards it will be very slow (software fallback?) if using the fglrx driver or it is ignored if using Mesa (which results in e.g. very bright parts becoming black).
author reimar
date Thu, 02 May 2013 19:44:29 +0000
parents d4b701cdd763
children 7ecb608a5943
files libvo/csputils.c libvo/gl_common.c
diffstat 2 files changed, 19 insertions(+), 18 deletions(-) [+]
line wrap: on
line diff
--- a/libvo/csputils.c	Wed May 01 22:45:26 2013 +0000
+++ b/libvo/csputils.c	Thu May 02 19:44:29 2013 +0000
@@ -137,18 +137,22 @@
   }
 }
 
+static float int2pos(int i, int size) {
+  if (i == 0) return 0;
+  if (i == size - 1) return 1;
+  return (i + 0.5) / size;
+}
+
 //! size of gamma map use to avoid slow exp function in gen_yuv2rgb_map
 #define GMAP_SIZE (1024)
 /**
  * \brief generate a 3D YUV -> RGB map
  * \param params struct containing parameters like brightness, gamma, ...
- * \param map where to store map. Must provide space for (size + 2)^3 elements
- * \param size size of the map, excluding border
+ * \param map where to store map. Must provide space for size^3 elements
+ * \param size size of the map
  */
 void mp_gen_yuv2rgb_map(struct mp_csp_params *params, unsigned char *map, int size) {
   int i, j, k, l;
-  float step = 1.0 / size;
-  float y, u, v;
   float yuv2rgb[3][4];
   unsigned char gmaps[3][GMAP_SIZE];
   mp_gen_gamma_map(gmaps[0], GMAP_SIZE, params->rgamma);
@@ -158,20 +162,17 @@
   for (i = 0; i < 3; i++)
     for (j = 0; j < 4; j++)
       yuv2rgb[i][j] *= GMAP_SIZE - 1;
-  v = 0;
-  for (i = -1; i <= size; i++) {
-    u = 0;
-    for (j = -1; j <= size; j++) {
-      y = 0;
-      for (k = -1; k <= size; k++) {
+  for (i = 0; i < size; i++) {
+    float v = int2pos(i, size);
+    for (j = 0; j < size; j++) {
+      float u = int2pos(j, size);
+      for (k = 0; k < size; k++) {
+        float y = int2pos(k, size);
         for (l = 0; l < 3; l++) {
           float rgb = yuv2rgb[l][COL_Y] * y + yuv2rgb[l][COL_U] * u + yuv2rgb[l][COL_V] * v + yuv2rgb[l][COL_C];
           *map++ = gmaps[l][av_clip(rgb, 0, GMAP_SIZE - 1)];
         }
-        y += (k == -1 || k == size - 1) ? step / 2 : step;
       }
-      u += (j == -1 || j == size - 1) ? step / 2 : step;
     }
-    v += (i == -1 || i == size - 1) ? step / 2 : step;
   }
 }
--- a/libvo/gl_common.c	Wed May 01 22:45:26 2013 +0000
+++ b/libvo/gl_common.c	Thu May 02 19:44:29 2013 +0000
@@ -1239,7 +1239,7 @@
       break;
     case YUV_CONVERSION_FRAGMENT_LOOKUP3D:
       {
-        int sz = LOOKUP_3DRES + 2; // texture size including borders
+        int sz = LOOKUP_3DRES; // texture size
         if (!mpglTexImage3D) {
           mp_msg(MSGT_VO, MSGL_ERR, "[gl] Missing 3D texture function!\n");
           break;
@@ -1250,14 +1250,14 @@
         mp_gen_yuv2rgb_map(&params->csp_params, lookup_data, LOOKUP_3DRES);
         glAdjustAlignment(sz);
         mpglPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
-        mpglTexImage3D(GL_TEXTURE_3D, 0, 3, sz, sz, sz, 1,
+        mpglTexImage3D(GL_TEXTURE_3D, 0, 3, sz, sz, sz, 0,
                        GL_RGB, GL_UNSIGNED_BYTE, lookup_data);
         mpglTexParameterf(GL_TEXTURE_3D, GL_TEXTURE_PRIORITY, 1.0);
         mpglTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
         mpglTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
-        mpglTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-        mpglTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_T, GL_CLAMP);
-        mpglTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_R, GL_CLAMP);
+        mpglTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+        mpglTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
+        mpglTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
         mpglActiveTexture(GL_TEXTURE0);
         texs[0] += '0';
       }