]> de.git.xonotic.org Git - voretournament/voretournament.git/blobdiff - misc/mediasource/netradiant-src/contrib/gtkgensurf/bitmap.cpp
Move the netradiant and fteqcc sources
[voretournament/voretournament.git] / misc / mediasource / netradiant-src / contrib / gtkgensurf / bitmap.cpp
diff --git a/misc/mediasource/netradiant-src/contrib/gtkgensurf/bitmap.cpp b/misc/mediasource/netradiant-src/contrib/gtkgensurf/bitmap.cpp
new file mode 100644 (file)
index 0000000..038d93a
--- /dev/null
@@ -0,0 +1,434 @@
+/*
+GenSurf plugin for GtkRadiant
+Copyright (C) 2001 David Hyde, Loki software and qeradiant.com
+
+This library is free software; you can redistribute it and/or
+modify it under the terms of the GNU Lesser General Public
+License as published by the Free Software Foundation; either
+version 2.1 of the License, or (at your option) any later version.
+
+This library is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+Lesser General Public License for more details.
+
+You should have received a copy of the GNU Lesser General Public
+License along with this library; if not, write to the Free Software
+Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+*/
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <math.h>
+#include "gensurf.h"
+
+void GenerateBitmapMapping ()
+{
+  double              value;
+  double              C0, C1;
+  double              x, y;
+  int                 i, j;
+  int                 O00,O01,O10,O11;
+  int                 r0, r1, c0, c1;
+  int                 color;
+  unsigned char       *colors;
+
+  if (!gbmp.colors)
+    return;
+
+  colors = gbmp.colors;
+
+  for (j=0; j<=NV; j++)
+  {
+    y  = (double)(j*(gbmp.height-1))/(double)NV;
+    r0 = (int)floor(y);
+    r1 = (int)ceil(y);
+    for (i=0; i<=NH; i++)
+    {
+      x = (double)(i*(gbmp.width-1))/(double)NH;
+      c0 = (int)floor(x);
+      c1 = (int)ceil(x);
+      O00 = r0*gbmp.width + c0;
+      O01 = r0*gbmp.width + c1;
+      O10 = r1*gbmp.width + c0;
+      O11 = r1*gbmp.width + c1;
+      C0 = (double)colors[O00] + (double)(colors[O01]-colors[O00])*(x-(double)c0);
+      C1 = (double)colors[O10] + (double)(colors[O11]-colors[O10])*(x-(double)c0);
+      color = (int)(C0 + (C1-C0)*(y-r0));
+
+      value = CalculateSnapValue(gbmp.black_value + color*((gbmp.white_value-gbmp.black_value)/255.));
+
+      switch(Plane)
+      {
+      case PLANE_XZ0:
+      case PLANE_XZ1:
+        xyz[i][j].p[1] = value;
+        break;
+      case PLANE_YZ0:
+      case PLANE_YZ1:
+        xyz[i][j].p[0] = value;
+        break;
+      default:
+        xyz[i][j].p[2] = value;
+      }
+    }
+  }
+}
+
+static unsigned char* OpenBitmapFile ()
+{
+#define INVALID_FORMAT do{\
+  fprintf(stderr,"%s:%d: Error file '%s' is malformed.\n",__FILE__,__LINE__,gbmp.name);\
+  fclose(fp);\
+  return NULL;\
+}while(0);
+
+  int32_t bmWidth;
+  int32_t bmHeight;
+  uint16_t bmPlanes;
+  uint16_t bmBitsPixel;
+  uint8_t m1,m2;
+  uint32_t sizeimage;
+  int16_t res1,res2;
+  int32_t filesize, pixoff;
+  int32_t bmisize, compression;
+  int32_t xscale, yscale;
+  int32_t colors, impcol;
+  uint32_t m_bytesRead = 0;
+  unsigned char *image;
+  FILE *fp;
+
+  fp = fopen (gbmp.name, "rb");
+  if (fp == NULL)
+  {
+         fprintf(stderr,"Error: Invalid filename '%s'\n",gbmp.name);
+         return NULL;
+  }
+
+  long rc;
+  rc = fread(&m1, 1, 1, fp);
+  m_bytesRead++;
+  if (rc == -1)
+  INVALID_FORMAT;
+
+  rc = fread(&m2, 1, 1, fp);
+  m_bytesRead++;
+  if ((m1 != 'B') || (m2 != 'M'))
+  INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(filesize),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint16_t*)&(res1),2,1,fp); m_bytesRead+=2;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint16_t*)&(res2),2,1,fp); m_bytesRead+=2;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(pixoff),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(bmisize),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t  *)&(bmWidth),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(bmHeight),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint16_t*)&(bmPlanes),2,1,fp); m_bytesRead+=2;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint16_t*)&(bmBitsPixel),2,1,fp); m_bytesRead+=2;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(compression),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(sizeimage),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(xscale),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(yscale),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(colors),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  rc = fread((uint32_t*)&(impcol),4,1,fp); m_bytesRead+=4;
+  if (rc != 1) INVALID_FORMAT;
+
+  if (bmBitsPixel != 8)
+  {
+    g_FuncTable.m_pfnMessageBox (g_pWnd, "This is not an 8-bit image. GenSurf can't use it.",
+                                 "Bitmap", eMB_OK, eMB_ICONWARNING);
+    fclose(fp);
+    return NULL; 
+  }
+
+  if (colors == 0)
+    colors = 1 << bmBitsPixel;
+
+  if (bmBitsPixel != 24)
+  {
+    int i;
+    for (i = 0; i < colors; i++)
+    {
+      unsigned char r ,g, b, dummy;
+
+      rc = fread(&b, 1, 1, fp);
+      m_bytesRead++;
+      if (rc!=1)
+      {
+              INVALID_FORMAT;
+      }
+
+      rc = fread(&g, 1, 1, fp); 
+      m_bytesRead++;
+      if (rc!=1)
+      {
+              INVALID_FORMAT;
+      }
+
+      rc = fread(&r, 1, 1, fp); 
+      m_bytesRead++;
+      if (rc != 1)
+      {
+              INVALID_FORMAT;
+      }
+
+      rc = fread(&dummy, 1, 1, fp); 
+      m_bytesRead++;
+      if (rc != 1)
+      {
+              INVALID_FORMAT;
+      }
+    }
+  }
+
+  if ((long)m_bytesRead > pixoff)
+  {
+          INVALID_FORMAT;
+  }
+
+  while ((long)m_bytesRead < pixoff)
+  {
+    char dummy;
+    fread(&dummy,1,1,fp);
+    m_bytesRead++;
+  }
+
+  int w = bmWidth;
+  int h = bmHeight;
+
+  // set the output params
+  image = (unsigned char*)malloc(w*h);
+
+  if (image != NULL) 
+  {
+    unsigned char* outbuf = image;
+    long row = 0;
+    long rowOffset = 0;
+
+    if (compression == 0) // BI_RGB
+    {
+      for (row = 0; row < bmHeight; row++)
+      {
+        // which row are we working on?
+        rowOffset = (long unsigned)row*w;                                                    
+
+        {
+          // pixels are packed as 1 , 4 or 8 bit vals. need to unpack them
+          int bit_count = 0;
+          unsigned long mask = (1 << bmBitsPixel) - 1;
+          unsigned char inbyte = 0;
+
+          for (int col=0;col<w;col++)
+          {
+            int pix = 0;
+
+            // if we need another byte
+            if (bit_count <= 0)
+            {
+              bit_count = 8;
+              if (fread(&inbyte,1,1,fp) != 1)
+              {
+                free(image);
+                INVALID_FORMAT;
+              }
+              m_bytesRead++;
+            }
+
+            // keep track of where we are in the bytes
+            bit_count -= bmBitsPixel;
+            pix = ( inbyte >> bit_count) & mask;
+
+            // lookup the color from the colormap - stuff it in our buffer
+            // swap red and blue
+            *(outbuf + rowOffset + col) = pix;
+          }
+
+          // read DWORD padding
+          while ((m_bytesRead-pixoff)&3)
+          {
+            char dummy;
+            if (fread(&dummy,1,1,fp)!=1)
+            {
+              free(image);
+              INVALID_FORMAT;
+            }
+            m_bytesRead++;
+          }
+        }
+      }
+    }
+    else    // compression != 0
+    {
+      int i, x = 0;
+      unsigned char c, c1 = 0, *pp;
+      row = 0;
+      pp = outbuf;
+
+      if (bmBitsPixel == 8)
+      {
+        while (row < bmHeight)
+        {
+          c = getc(fp);
+
+          if (c)
+          {
+            // encoded mode
+            c1 = getc(fp);
+            for (i = 0; i < c; x++, i++)
+            {
+              *pp = c1; pp++;
+            }
+          }
+          else
+          {
+            // c==0x00,  escape codes
+            c = getc(fp);
+
+            if (c == 0x00) // end of line
+            {
+              row++;
+              x = 0;
+              pp = outbuf + row*bmWidth;
+            }
+            else if (c == 0x01)
+              break; // end of pic
+            else if (c == 0x02) // delta
+            {
+              c = getc(fp);
+              x += c;
+              c = getc(fp);
+              row += c;
+              pp = outbuf + x + row*bmWidth;
+            }
+            else // absolute mode
+            {
+              for (i = 0; i < c; x++, i++)
+              {
+                c1 = getc(fp);
+                *pp = c1; pp++;
+              }
+
+              if (c & 1)
+                getc(fp); // odd length run: read an extra pad byte
+            }
+          }
+        }
+      }
+      else if (bmBitsPixel == 4)
+      {
+        while (row < bmHeight)
+        {
+          c = getc(fp);
+
+          if (c)
+          {
+            // encoded mode
+            c1 = getc(fp);
+            for (i = 0; i < c; x++, i++)
+            {
+              *pp = (i&1) ? (c1 & 0x0f) : ((c1>>4)&0x0f); pp++;
+            }
+          }
+          else
+          {
+            // c==0x00,  escape codes
+            c = getc(fp);
+
+            if (c == 0x00) // end of line
+            {
+              row++;
+              x = 0;
+              pp = outbuf + bmHeight*bmWidth;
+            }
+            else if (c == 0x01)
+              break; // end of pic
+            else if (c == 0x02) // delta
+            {
+              c = getc(fp);
+              x += c;
+              c = getc(fp);
+              row += c;
+              pp = outbuf + x + row*bmWidth;
+            }
+            else // absolute mode
+            {
+              for (i = 0; i < c; x++, i++)
+              {
+                if ((i&1) == 0)
+                  c1 = getc(fp);
+                *pp = (i&1) ? (c1 & 0x0f) : ((c1>>4)&0x0f); pp++;
+              }
+
+              if (((c&3) == 1) || ((c&3) == 2))
+                getc(fp); // odd length run: read an extra pad byte
+            }
+          }
+        }
+      }
+    }
+  }
+  fclose(fp);
+
+  gbmp.width = w;
+  gbmp.height = h;
+  if(gbmp.colors)
+       free(gbmp.colors);
+  gbmp.colors = image;
+  return image;
+
+
+}
+
+bool OpenBitmap ()
+{
+
+  OpenBitmapFile ();
+
+  if (!gbmp.colors)
+  {
+    char Text[256];
+
+    sprintf (Text, "Error opening %s", gbmp.name);
+    g_FuncTable.m_pfnMessageBox (g_pWnd, Text, "Bitmap", eMB_OK, eMB_ICONWARNING);
+    strcpy (gbmp.name, "");
+  }
+
+  if (g_pWnd)
+  {
+    gtk_entry_set_text (GTK_ENTRY (g_object_get_data (G_OBJECT (g_pWnd), "bmp_file")), gbmp.name);
+    gtk_widget_set_sensitive (GTK_WIDGET (g_object_get_data (G_OBJECT (g_pWnd), "bmp_reload")),
+                              strlen (gbmp.name) ? TRUE : FALSE);
+
+    UpdatePreview (true);
+  }
+
+  return (gbmp.colors != NULL);
+}