gallium: consolidate the bitmap->texel conversion code
authorBrian Paul <brian.paul@tungstengraphics.com>
Wed, 30 Apr 2008 16:10:44 +0000 (10:10 -0600)
committerBrian Paul <brian.paul@tungstengraphics.com>
Wed, 30 Apr 2008 16:10:44 +0000 (10:10 -0600)
src/mesa/state_tracker/st_cb_bitmap.c

index e9d375dc58a5645e969c1a8dd2118c4709a6ac9f..d73cd4abfa9e12b2eeed08961e5a8475e014c59f 100644 (file)
@@ -224,58 +224,37 @@ combined_bitmap_fragment_program(GLcontext *ctx)
 
 
 /**
- * Create a texture which represents a bitmap image.
+ * Copy user-provide bitmap bits into texture buffer, expanding
+ * bits into texels.
+ * "On" bits will set texels to 0xff.
+ * "Off" bits will not modify texels.
+ * Note that the image is actually going to be upside down in
+ * the texture.  We deal with that with texcoords.
  */
-static struct pipe_texture *
-make_bitmap_texture(GLcontext *ctx, GLsizei width, GLsizei height,
-                    const struct gl_pixelstore_attrib *unpack,
-                    const GLubyte *bitmap)
+static void
+unpack_bitmap(struct st_context *st,
+              GLint px, GLint py, GLsizei width, GLsizei height,
+              const struct gl_pixelstore_attrib *unpack,
+              const GLubyte *bitmap,
+              ubyte *destBuffer, uint destStride)
 {
-   struct pipe_context *pipe = ctx->st->pipe;
-   struct pipe_screen *screen = pipe->screen;
-   struct pipe_surface *surface;
-   ubyte *dest;
-   struct pipe_texture *pt;
-   int row, col;
-
-   /* PBO source... */
-   bitmap = _mesa_map_bitmap_pbo(ctx, unpack, bitmap);
-   if (!bitmap) {
-      return NULL;
-   }
+   GLint row, col;
 
-   /**
-    * Create texture to hold bitmap pattern.
-    */
-   pt = st_texture_create(ctx->st, PIPE_TEXTURE_2D, ctx->st->bitmap.tex_format,
-                          0, width, height, 1, 0);
-   if (!pt) {
-      _mesa_unmap_bitmap_pbo(ctx, unpack);
-      return NULL;
-   }
-
-   surface = screen->get_tex_surface(screen, pt, 0, 0, 0);
-
-   /* map texture surface */
-   dest = pipe_surface_map(surface);
-
-   /* Put image into texture surface.
-    * Note that the image is actually going to be upside down in
-    * the texture.  We deal with that with texcoords.
-    */
+#define SET_PIXEL(COL, ROW) \
+   destBuffer[(py + (ROW)) * destStride + px + (COL)] = 0x0;
 
    for (row = 0; row < height; row++) {
       const GLubyte *src = (const GLubyte *) _mesa_image_address2d(unpack,
                  bitmap, width, height, GL_COLOR_INDEX, GL_BITMAP, row, 0);
-      ubyte *destRow = dest + row * surface->pitch;
 
       if (unpack->LsbFirst) {
          /* Lsb first */
          GLubyte mask = 1U << (unpack->SkipPixels & 0x7);
          for (col = 0; col < width; col++) {
 
-            /* set texel to 255 if bit is set */
-            destRow[col] = (*src & mask) ? 0x0 : 0xff;
+            if (*src & mask) {
+               SET_PIXEL(col, row);
+            }
 
             if (mask == 128U) {
                src++;
@@ -295,8 +274,9 @@ make_bitmap_texture(GLcontext *ctx, GLsizei width, GLsizei height,
          GLubyte mask = 128U >> (unpack->SkipPixels & 0x7);
          for (col = 0; col < width; col++) {
 
-            /* set texel to 255 if bit is set */
-            destRow[col] =(*src & mask) ? 0x0 : 0xff;
+            if (*src & mask) {
+               SET_PIXEL(col, row);
+            }
 
             if (mask == 1U) {
                src++;
@@ -314,6 +294,50 @@ make_bitmap_texture(GLcontext *ctx, GLsizei width, GLsizei height,
 
    } /* row */
 
+#undef SET_PIXEL
+}
+
+
+/**
+ * Create a texture which represents a bitmap image.
+ */
+static struct pipe_texture *
+make_bitmap_texture(GLcontext *ctx, GLsizei width, GLsizei height,
+                    const struct gl_pixelstore_attrib *unpack,
+                    const GLubyte *bitmap)
+{
+   struct pipe_context *pipe = ctx->st->pipe;
+   struct pipe_screen *screen = pipe->screen;
+   struct pipe_surface *surface;
+   ubyte *dest;
+   struct pipe_texture *pt;
+
+   /* PBO source... */
+   bitmap = _mesa_map_bitmap_pbo(ctx, unpack, bitmap);
+   if (!bitmap) {
+      return NULL;
+   }
+
+   /**
+    * Create texture to hold bitmap pattern.
+    */
+   pt = st_texture_create(ctx->st, PIPE_TEXTURE_2D, ctx->st->bitmap.tex_format,
+                          0, width, height, 1, 0);
+   if (!pt) {
+      _mesa_unmap_bitmap_pbo(ctx, unpack);
+      return NULL;
+   }
+
+   surface = screen->get_tex_surface(screen, pt, 0, 0, 0);
+
+   /* map texture surface */
+   dest = pipe_surface_map(surface);
+
+   /* Put image into texture surface */
+   memset(dest, 0xff, height * surface->pitch);
+   unpack_bitmap(ctx->st, 0, 0, width, height, unpack, bitmap,
+                 dest, surface->pitch);
+
    _mesa_unmap_bitmap_pbo(ctx, unpack);
 
    /* Release surface */
@@ -585,7 +609,6 @@ accum_bitmap(struct st_context *st,
              const GLubyte *bitmap )
 {
    struct bitmap_cache *cache = st->bitmap.cache;
-   int row, col;
    int px = -999, py;
 
    if (width > BITMAP_CACHE_WIDTH ||
@@ -624,60 +647,8 @@ accum_bitmap(struct st_context *st,
    if (y + height > cache->ymax)
       cache->ymax = y + height;
 
-   /* XXX try to combine this code with code in make_bitmap_texture() */
-#define SET_PIXEL(COL, ROW) \
-   cache->buffer[(py + (ROW)) * BITMAP_CACHE_WIDTH + px + (COL)] = 0x0;
-
-   for (row = 0; row < height; row++) {
-      const GLubyte *src = (const GLubyte *) _mesa_image_address2d(unpack,
-                 bitmap, width, height, GL_COLOR_INDEX, GL_BITMAP, row, 0);
-
-      if (unpack->LsbFirst) {
-         /* Lsb first */
-         GLubyte mask = 1U << (unpack->SkipPixels & 0x7);
-         for (col = 0; col < width; col++) {
-
-            if (*src & mask) {
-               SET_PIXEL(col, row);
-            }
-
-            if (mask == 128U) {
-               src++;
-               mask = 1U;
-            }
-            else {
-               mask = mask << 1;
-            }
-         }
-
-         /* get ready for next row */
-         if (mask != 1)
-            src++;
-      }
-      else {
-         /* Msb first */
-         GLubyte mask = 128U >> (unpack->SkipPixels & 0x7);
-         for (col = 0; col < width; col++) {
-
-            if (*src & mask) {
-               SET_PIXEL(col, row);
-            }
-
-            if (mask == 1U) {
-               src++;
-               mask = 128U;
-            }
-            else {
-               mask = mask >> 1;
-            }
-         }
-
-         /* get ready for next row */
-         if (mask != 128)
-            src++;
-      }
-
-   } /* row */
+   unpack_bitmap(st, px, py, width, height, unpack, bitmap,
+                 cache->buffer, BITMAP_CACHE_WIDTH);
 
    return GL_TRUE; /* accumulated */
 }