about summary refs log tree commit diff
path: root/converter/pbm/pbmtosunicon.c
diff options
context:
space:
mode:
Diffstat (limited to 'converter/pbm/pbmtosunicon.c')
-rw-r--r--converter/pbm/pbmtosunicon.c165
1 files changed, 165 insertions, 0 deletions
diff --git a/converter/pbm/pbmtosunicon.c b/converter/pbm/pbmtosunicon.c
new file mode 100644
index 00000000..95deab7c
--- /dev/null
+++ b/converter/pbm/pbmtosunicon.c
@@ -0,0 +1,165 @@
+/* pbmtosunicon.c - read a PBM image and produce a Sun icon file
+**
+** Copyright (C) 1988 by Jef Poskanzer.
+**
+** Permission to use, copy, modify, and distribute this software and its
+** documentation for any purpose and without fee is hereby granted, provided
+** that the above copyright notice appear in all copies and that both that
+** copyright notice and this permission notice appear in supporting
+** documentation.  This software is provided "as is" without express or
+** implied warranty.
+*/
+
+/* 2006.10 (afu)
+   Changed bitrow from plain to raw, read function from pbm_readpbmrow() to
+   pbm_readpbmrow_packed.  Applied wordint to scoop up 16 bit output items.
+   putitem changed to better express the output format.
+   Retired bitwise transformation functions.
+*/
+
+#include "pm_config.h"
+#include "pbm.h"
+
+static struct ItemPutter {
+    unsigned short int itemBuff[8];
+    unsigned int       itemCnt;    /* takes values 0 to 8 */
+    FILE *             putFp;
+} ip;
+
+
+
+static void
+putinit(FILE * const ofP) {
+    ip.putFp   = ofP;
+    ip.itemCnt = 0;
+}
+
+
+
+static void
+putitem(uint16_t const item) {
+
+    if (ip.itemCnt == 8 ) {
+        /* Buffer is full.  Write out one line. */
+        int rc;
+    
+        rc = fprintf(ip.putFp,
+                     "\t0x%04x,0x%04x,0x%04x,0x%04x,"
+                     "0x%04x,0x%04x,0x%04x,0x%04x,\n",
+                     ip.itemBuff[0], ip.itemBuff[1],
+                     ip.itemBuff[2], ip.itemBuff[3],
+                     ip.itemBuff[4], ip.itemBuff[5],
+                     ip.itemBuff[6], ip.itemBuff[7]);
+        if (rc < 0)        
+           pm_error("fprintf() failed to write Icon bitmap");
+           
+        ip.itemCnt = 0;
+    }
+    ip.itemBuff[ip.itemCnt++] = item & 0xffff;
+        /* Only lower 16 bits are used */
+}
+
+
+
+static void
+putterm(void) {
+
+    unsigned int i;
+
+    for (i = 0; i < ip.itemCnt; ++i) {
+        int rc;
+        rc = fprintf(ip.putFp, "%s0x%04x%c", i == 0  ? "\t" : "",
+                     ip.itemBuff[i],
+                     i == ip.itemCnt - 1 ? '\n' : ',');
+        if (rc < 0)        
+            pm_error("fprintf() failed to write Icon bitmap");
+    }
+}     
+
+
+
+static void
+writeIconHeader(FILE *       const ofP,
+                unsigned int const width,
+                unsigned int const height) {
+
+    int rc;
+
+    rc = fprintf(ofP,
+                 "/* Format_version=1, Width=%u, Height=%u", width, height);
+    if (rc < 0)
+        pm_error("fprintf() failed to write Icon header");
+        
+    rc = fprintf(ofP, ", Depth=1, Valid_bits_per_item=16\n */\n");
+    if (rc < 0)
+        pm_error("fprintf() failed to write Icon header");
+}
+
+
+
+static void
+writeIcon(FILE *       const ifP,
+          unsigned int const cols,
+          unsigned int const rows,
+          int          const format,
+          FILE *       const ofP) {
+
+    unsigned int const items = (cols + 15) / 16;
+    unsigned int const pad = items * 16 - cols;
+
+    unsigned char * const bitrow = pbm_allocrow_packed(items * 16);
+    unsigned int row;
+
+    bitrow[0] = bitrow[items * 2 - 1] = 0;
+
+    writeIconHeader(ofP, cols + pad, rows);
+
+    putinit(ofP);
+
+    for (row = 0; row < rows; ++row) {
+        unsigned int itemSeq;
+
+        pbm_readpbmrow_bitoffset(ifP, bitrow, cols, format, pad/2);
+
+        for (itemSeq = 0; itemSeq < items; ++itemSeq) {
+            /* Read bits from bitrow, send to format & print function. */
+            
+            putitem((bitrow[itemSeq*2]<<8) + bitrow[itemSeq*2+1]);
+        }
+    }
+    putterm();
+    pbm_freerow_packed(bitrow);
+}
+
+
+
+int
+main(int argc,
+     char * argv[]) {
+
+    FILE * ifP;
+    int rows, cols;
+    int format;
+    const char * inputFileName;
+
+    pbm_init(&argc, argv);
+
+    if (argc-1 > 1)
+        pm_error("Too many arguments (%u).  "
+                 "Only argument is optional input file", argc-1);
+    if (argc-1 == 1)
+        inputFileName = argv[1];
+    else
+        inputFileName = "-";
+    
+    ifP = pm_openr(inputFileName);
+
+    pbm_readpbminit(ifP, &cols, &rows, &format);
+
+    writeIcon(ifP, cols, rows, format, stdout);
+
+    pm_close(ifP);
+
+    return 0;
+}
+