home *** CD-ROM | disk | FTP | other *** search
/ Club Amiga de Montreal - CAM / CAM_CD_1.iso / files / 223.lha / IffToPostScript / ifftops.c < prev    next >
C/C++ Source or Header  |  1989-04-02  |  21KB  |  752 lines

  1. /* IFFTOPS - ILBM IFF format file to PostScript translator.    */
  2. /*    Version 3.0 - LeRoy Fundingsland - 12/12/88 - SRC    */
  3. /*                                */
  4. /*    This code has been compiled and tested under both Sun    */
  5. /*    UNIX (V3.5) and Commodore AmigaDOS (V1.2). On the    */
  6. /*    Amiga the Lattice 4.0 compiler was used ("lc -Lm").    */
  7.  
  8. /*              CLAZ.c  v2.0                     */
  9. /*              by Steve Ludtke                  */
  10. /*              Created : 05/31/87               */
  11.  
  12. /*    Re-written Oct-Dec 1988 by LeRoy Fundingsland        */
  13. /*        Supercomputing Research Center            */
  14. /*            Lanham, MD                */
  15. /*        funding@metropolis.super.org            */
  16. /*                                */
  17. /*    Changes:                        */
  18. /*    - code re-structured for readability and maintain-    */
  19. /*        ability (my opinion (mostly:-))            */
  20. /*    - comments added for readability (but mostly just so I    */
  21. /*        could understand the code)            */
  22. /*    - code extended, with IFDEFs, to be compilable on SUN    */
  23. /*        systems (or nearly any 4.2BSD derived system,    */
  24. /*        I expect)                    */
  25. /*    - extended to generate color postscript output (as of    */
  26. /*        the above date, color postscript output        */
  27. /*        devices may be pretty rare but we have one and    */
  28. /*        I think they will be be increasingly common in    */
  29. /*        the future)                    */
  30. /*    - code extended, again with IFDEFs, to contain a rough    */
  31. /*        attempt at reducing the grainyness of the    */
  32. /*        output image (ref. "SMOOTH_INCLUDE")        */
  33. /*    - added the function for the image to be arbitrarily    */
  34. /*        rotated                        */
  35. /*                                */
  36. /*    TODO:                            */
  37. /*    - place all of the initialization of default        */
  38. /*        values to happen at compile time        */
  39. /*    - make sure that every value in the "cmap" array is    */
  40. /*        non-negative                    */
  41. /*    - QUESTION: when an Amiga process exits is the        */
  42. /*        programmer guaranteed that all system resources    */
  43. /*        are released? (specifically MALLOCed memory)?    */
  44.  
  45.             /* the following DEFINE is for        /* 1 */
  46.             /* IFDEFing code which is specific to    /* 1 */
  47.             /* the QMS ColorScript-100 laser    /* 1 */
  48.             /* printer.                /* 1 */
  49. #define QMS                            /* 1 */
  50. #define SMOOTH_INCLUDE                        /* 1 */
  51.             /* The code in this file has been    /* 1 */
  52.             /* constructed so that one, and only    /* 1 */
  53.             /* one, of the following "environment"    /* 1 */
  54.             /* "define"s should be included in the    /* 1 */
  55.             /* active code at any time.        /* 1 */
  56. /*                                /# 1 #/
  57. #define AMIGA                            /* 1 */
  58. #define SUN                            /* 1 */
  59.  
  60. #include<stdio.h>
  61. #include<math.h>
  62.  
  63. #ifdef AMIGA                            /* 1 */
  64. #undef NULL                            /* 1 */
  65. #include<exec/types.h>
  66. #endif AMIGA                            /* 1 */
  67. #ifdef SUN                            /* 1 */
  68. #define BYTE    char                        /* 1 */
  69. #define UBYTE    unsigned char                    /* 1 */
  70. #define WORD    short                        /* 1 */
  71. #define UWORD    unsigned short                    /* 1 */
  72. #define LONG    int                        /* 1 */
  73. #endif SUN                            /* 1 */
  74.  
  75.             /* define IFF structures */
  76. struct CMAP {
  77.     UBYTE r,g,b;
  78. };
  79.  
  80. struct BMHD {
  81.     UWORD w,h;
  82.     WORD x,y;
  83.     UBYTE npl;
  84.     UBYTE masking,compression,pad1;
  85.     UWORD tcolor;
  86.     UBYTE xas,yas;
  87.     WORD pWid,pHig;
  88. };
  89.  
  90. char hex[] = { '0', '1', '2', '3', '4', '5', '6', '7',        /* 1 */
  91.         '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};    /* 1 */
  92.                                 /* 1 */
  93. #ifdef SUN                            /* 1 */
  94. #define TRUE    1                        /* 1 */
  95. #define FALSE    0                        /* 1 */
  96. #endif SUN                            /* 1 */
  97. int blacknwhite = TRUE;                        /* 1 */
  98.                                 /* 1 */
  99. char *filename_err1 =                        /* 1 */
  100.     "ERROR: Too many file names on the command line\n";    /* 1 */
  101. char *filename_data1 =                        /* 1 */
  102.     "\t(input=\"%s\", output=\"%s\", error string=\"%s\")\n\n";    /* 1 */
  103.  
  104.             /* smoothing related declarations    /* 1 */
  105. int smooth = 0;                            /* 1 */
  106. int width, height;                        /* 1 */
  107.             /* pointers to storage where pixel    /* 1 */
  108.             /* values are held during smoothing    /* 1 */
  109. char *pixelrow, *smoothrow;                    /* 1 */
  110.  
  111.  
  112. char *malloc();
  113. void putval1();                            /* 1 */
  114. void putval2();                            /* 1 */
  115.  
  116. void                                /* 1 */
  117. main(argc, argv)
  118.     int argc; char *argv[];{
  119.     struct BMHD mhd;
  120.     long len1, len2, cnt, m, h, i, j, k, lr, lb, lg,
  121.         x1, x2, y1, y2, showpage;
  122.     int fl1, b;
  123.     int rotate = 0;                        /* 1 */
  124.     BYTE t;
  125.     UBYTE cmap[100];
  126.     char *raster=NULL, *rp, *infile=NULL, inspace[80],    /* 1 */
  127.         *outfile=NULL, c, *misc=NULL;            /* 1 */
  128.     LONG msc1[3], msc2[2];                    /* 1 */
  129.     FILE *fin, *fout;
  130.  
  131.     if(argc == 1){                        /* 1 */
  132. usage:                                /* 1 */
  133.         printf("Usage is: ifftops ");            /* 1 */
  134.         printf("[-c] [-h]");                /* 1 */
  135. #ifdef SMOOTH_INCLUDE                        /* 1 */
  136.         printf(" [-s]");                /* 1 */
  137. #endif SMOOTH_INCLUDE                        /* 1 */
  138.         printf(" [-r <degrees>]\n");            /* 1 */
  139.         printf("\t\t[-p <x-start>,<y-start>,");        /* 1 */
  140.         printf("<x-scale>,<y-scale>]\n");        /* 1 */
  141.         printf("\t\t<input file> [<output-file>]\n");    /* 1 */
  142.         if(raster != NULL)                /* 1 */
  143.             free(raster);                /* 1 */
  144.         if(misc != NULL)                /* 1 */
  145.             free(misc);                /* 1 */
  146.         exit();                        /* 1 */
  147.     }                            /* 1 */
  148.  
  149.     showpage=1; x1=10; y1=10; x2=550; y2=480;        /* 1 */
  150. #ifdef QMS                            /* 1 */
  151.     y1 = (14*72)/16;    /* mechanical paper handlng */    /* 1 */
  152. #endif QMS                            /* 1 */
  153.  
  154.             /* Get enough memory, figure out filespecs */
  155.     raster = malloc(200000);
  156.     if (raster == NULL)
  157.         { printf("Not enough memory. (1)\n"); exit(0); }/* 1 */
  158.     misc = malloc(2000);
  159.     if(misc == NULL)                    /* 1 */
  160.         { printf("Not enough memory. (2)\n"); exit(0); }/* 1 */
  161.  
  162.             /* parse command line arguments        */
  163.     for(argc--,argv++; argc > 0; argc--, argv++){        /* 1 */
  164.         if(argv[0][0] == '-'){                /* 1 */
  165.             switch(argv[0][1]){            /* 1 */
  166.             case 'c':    /* "color" output */    /* 1 */
  167.                 blacknwhite = FALSE;        /* 1 */
  168.                 break;                /* 1 */
  169.             case 'h':    /* "hold" printout */    /* 1 */
  170.                 showpage = FALSE;        /* 1 */
  171.                 break;                /* 1 */
  172.             case 'p':    /* "position" image */    /* 1 */
  173.                 if(argv[0][2] != 0)        /* 1 */
  174.                     goto bad_p_flag;    /* 1 */
  175.                 argc--; argv++;            /* 1 */
  176.                 if(argc < 1)            /* 1 */
  177.                     goto bad_p_flag;    /* 1 */
  178.                 i =                /* 1 */
  179.                 sscanf(argv[0],"%ld,%ld,%ld,%ld",/* 1 */
  180.                     &x1, &y1, &x2, &y2);    /* 1 */
  181.                 if(i != 4){            /* 1 */
  182. bad_p_flag:                printf("Bad format ");    /* 1 */
  183.                     printf("for 'p' flag\n");/* 1 */
  184.                     goto usage;        /* 1 */
  185.                 }                /* 1 */
  186.                 break;                /* 1 */
  187.             case 'r':    /* "rotate" image */    /* 1 */
  188.                 if(argv[0][2] != 0)        /* 1 */
  189.                     goto bad_r_flag;    /* 1 */
  190.                 argc--; argv++;            /* 1 */
  191.                 if(argc < 1)            /* 1 */
  192.                     goto bad_r_flag;    /* 1 */
  193.                 i =                /* 1 */
  194.                 sscanf(argv[0],"%ld",&rotate);    /* 1 */
  195.                 if(i != 1){            /* 1 */
  196. bad_r_flag:                printf("Bad format ");    /* 1 */
  197.                     printf("for 'r' flag\n");/* 1 */
  198.                     goto usage;        /* 1 */
  199.                 }                /* 1 */
  200.                 if(rotate >= 360  ||        /* 1 */
  201.                         rotate <= -360)    /* 1 */
  202.                     goto bad_r_flag;    /* 1 */
  203.                 break;                /* 1 */
  204. #ifdef SMOOTH_INCLUDE                        /* 1 */
  205.             case 's':    /* "smooth" image */    /* 1 */
  206. /*
  207.                 if(argv[0][2] == 0){        /* 1 */
  208.                     smooth = 1;        /* 1 */
  209. /*
  210.                     break;            /* 1 */
  211. /*
  212.                 }                /* 1 */
  213. #ifdef NEVERDEF
  214.                 sscanf(&argv[0][2], "%d", &smooth);
  215.                 if(smooth == 0)            /* 1 */
  216.                     goto usage;        /* 1 */
  217.                 if(smooth < 1  ||  smooth > 3){    /* 1 */
  218.                     printf("Invalid \"smooth\" ");
  219.                     printf("value.\n");    /* 1 */
  220.                     exit(1);        /* 1 */
  221.                 }                /* 1 */
  222. #endif NEVERDEF
  223.                 break;                /* 1 */
  224. #endif SMOOTH_INCLUDE                        /* 1 */
  225.             default:                /* 1 */
  226.                 printf("Unknown flag '%c'\n",    /* 1 */
  227.                         *argv[1]);    /* 1 */
  228.                 exit(1);            /* 1 */
  229.             }                    /* 1 */
  230.         }                        /* 1 */
  231.         else {        /* file designator */        /* 1 */
  232.                 /* maximum of two files allowed    /* 1 */
  233.                 /* the first one is the input    /* 1 */
  234.                 /* file, the second, if it    /* 1 */
  235.                 /* exists is the output file    /* 1 */
  236.             if(infile == NULL)            /* 1 */
  237.                 infile = *argv;            /* 1 */
  238.             else if(outfile == NULL)        /* 1 */
  239.                 outfile = *argv;        /* 1 */
  240.             else{                    /* 1 */
  241.                 printf(filename_err1);        /* 1 */
  242.                 printf(filename_data1, infile,    /* 1 */
  243.                     outfile, *argv);    /* 1 */
  244.                 goto usage;            /* 1 */
  245.             }                    /* 1 */
  246.         }                        /* 1 */
  247.     }        /* end of argument parsing FOR loop */    /* 1 */
  248.     if(infile == NULL){                    /* 1 */
  249.         printf("ERROR: input file name required.\n\n");    /* 1 */
  250.         goto usage;                    /* 1 */
  251.     }                            /* 1 */
  252.  
  253.     
  254.     printf("\n\n                IFFTOPS - IFF to POSTSCRIPT");
  255.     printf(" converter V3.0\n");
  256.     printf("                           By LeRoy Fundingsland\n");
  257.     printf("                             (via Steve Ludtke)\n");
  258.     printf("                          N\251 - No Copyright 1988\n");
  259.     printf("\n");
  260.     printf("File in : ");
  261.     if(infile != NULL)                    /* 1 */
  262.         printf("%s\n", infile);
  263.     else{        /* no input file supplied    */
  264.         infile = inspace;                /* 1 */
  265.         scanf("%s", infile);
  266.     }
  267.     if(outfile == NULL)                    /* 1 */
  268.         outfile = "out.ps";
  269.  
  270.     fin = fopen(infile, "r");
  271.     if(fin == NULL)
  272.         { printf("Sorry, can't open input file.\n"); exit(0); }
  273.     if ((fread((char *)msc1,12,1,fin)) == 0)        /* 1 */
  274.         { printf("Sorry, input file problem #1\n"); exit (0); }
  275. /*                                /# 1 #/
  276.     len1 = (long *)&msc1[4];
  277. */                                /* 1 */
  278.     len1 = msc1[1];                        /* 1 */
  279.     printf("main : %d,%4s\n", len1, (char *)&msc1[0]);    /* 1 */
  280.     cnt = 14;
  281.  
  282.     /* len1=# bytes in file according to IFF */
  283.     /* msc2=the name of the current chunk */
  284.     /* len2=# bytes in current chunk */
  285.     /* by the way, UNID is symply any chunk the program    */
  286.     /*    doesn't deal with */
  287.  
  288.             /* Reads in the IFF file : */
  289.  
  290.     while(cnt < len1){
  291.         fl1 = 0;
  292.         if ((fread((char *)msc2,8,1,fin)) == 0)        /* 1 */
  293.             {printf("Sorry, bad input file. \n"); exit(0);}
  294. /*                                /# 1 #/
  295.         len2 = (long *)&msc2[4];
  296. */                                /* 1 */
  297.         len2 = msc2[1];                    /* 1 */
  298.  
  299.         if (strncmp((char *)msc2,"CMAP",4) == 0) {    /* 1 */
  300.             if ((fread(cmap,len2,1,fin)) == 0)
  301.                 { printf("Sorry, bad CMAP. \n"); exit(0); }
  302.             printf("CMAP\n");
  303.             fl1 = 1;
  304.         }
  305.  
  306.         if (strncmp((char *)msc2,"BMHD",4) == 0) {    /* 1 */
  307.             if ((fread((char *)&mhd,len2,1,fin)) == 0)
  308.                 { printf("Sorry, bad BMHD. \n"); exit(0); }
  309.             printf("BMHD\n");
  310.             fl1 = 1;
  311.         }
  312.  
  313.         if (strncmp((char *)msc2,"BODY",4) == 0) {    /* 1 */
  314.             printf("BODY\n");
  315. #ifdef DEBUG                            /* 1 */
  316. printf("\t\tlength of BODY chunk (from file) = %d\n", len2);    /*999*/
  317. #endif DEBUG                            /* 1 */
  318.             fl1 = 1;
  319.             m = 0; rp = raster;
  320.             if (mhd.compression == 1) {
  321.                 while (m <= len2) {
  322.                     t = getc(fin); m++;
  323.                     if (t >= 0) {
  324.                         t++;
  325.                         fread(rp,(long) t,1,fin);
  326.                         rp += t;
  327.                         m += t;
  328.                     }
  329.                     if (t<0) {
  330.                         t=(-t)+1;
  331.                         c=getc(fin);
  332.                         m++;
  333.                         for (i=0; i<t; i++) {
  334.                             *rp=c; rp++;
  335.                         }
  336.                     }
  337.                 }
  338.             }
  339.             if (mhd.compression == 0) {
  340.                 if((fread(rp,len2,1,fin)) == 0){
  341.                     printf("Sorry, bad BODY. \n");
  342.                     exit(0);
  343.                 }
  344.                 printf("No Compression\n");
  345.             }
  346.             if (mhd.compression > 1) {
  347.                 printf("Sorry, unknown compression type.\n");
  348.                 exit(0);
  349.             }
  350.         }        /* end of "BODY" IF statement    */
  351.  
  352.         if (fl1 == 0) {
  353.             if (len2 > 2000) {
  354.                 printf("Sorry, UNID too long.\n");
  355.                 exit(0);
  356.             }
  357.             if ((fread(misc,len2,1,fin)) == 0) {
  358.                 printf("Sorry, UNID bad. \n");
  359.                 exit(0);
  360.             }
  361.             printf("UNID\n");
  362.         }
  363.     
  364.           cnt += len2;
  365.         cnt += 8;
  366.     }        /* end of IFF-file-reading WHILE loop    */
  367.  
  368. #ifdef DEBUG                            /* 1 */
  369. printf("Total bytes read into \"raster\" = %d\n", rp-raster);    /*999*/
  370. #endif DEBUG                            /* 1 */
  371.     fclose(fin);
  372.  
  373.             /* inform user if file already exists    /* 1 */
  374.             /* and is being appended to        /* 1 */
  375.     if((fout=fopen(outfile,"r")) != NULL){            /* 1 */
  376.         printf("Output file, \"%s\", already exists.\n",/* 1 */
  377.                         outfile);    /* 1 */
  378.         printf("Output is being appended to this file.\n");
  379.         fclose(fout);                    /* 1 */
  380.     }                            /* 1 */
  381.     if ((fout=fopen(outfile,"a")) == NULL) {
  382.         printf("Sorry, cannot open output file.\n");
  383.         exit(0);
  384.     }
  385.  
  386. /* Standard POSTSCRIPT program, the only part following the data is */
  387. /* the showpage command. */
  388.  
  389.     if(smooth){                        /* 1 */
  390.         width = mhd.w * 2;                /* 1 */
  391.         height = mhd.h * 2;                /* 1 */
  392.             /* the "pixelrow" array is sized at one    /* 1 */
  393.             /* byte for each pixel because it will    /* 1 */
  394.             /* hold the ASCII-HEX (see "hex" array)    /* 1 */
  395.             /* value for each pixel.        /* 1 */
  396.             /* (3 bytes for each pixel if color)    /* 1 */
  397.         if(blacknwhite == TRUE)                /* 1 */
  398.             pixelrow = malloc(width);        /* 1 */
  399.         else        /* color */            /* 1 */
  400.             pixelrow = malloc(width * 3);        /* 1 */
  401.         if(pixelrow == NULL)                /* 1 */
  402.         { printf("Not enough memory. (3)\n"); exit(0); }/* 1 */
  403.             /* the same for the "smoothrow" array    /* 1 */
  404.         if(blacknwhite == TRUE)                /* 1 */
  405.             smoothrow = malloc(width);        /* 1 */
  406.         else        /* color */            /* 1 */
  407.             smoothrow = malloc(width * 3);        /* 1 */
  408.         if(smoothrow == NULL)                /* 1 */
  409.         { printf("Not enough memory. (4)\n"); exit(0); }/* 1 */
  410.     }                            /* 1 */
  411.     else{                            /* 1 */
  412.         width = mhd.w;                    /* 1 */
  413.         height = mhd.h;                    /* 1 */
  414.     }                            /* 1 */
  415.                                 /* 1 */
  416.     fprintf(fout, "%%!\r");                    /* 1 */
  417.     fprintf(fout,"[0 0 0 0 0 0] defaultmatrix setmatrix\r");/* 1 */
  418.             /* the length of the postscript        /* 1 */
  419.             /* "picture string" (picstr) must equal    /* 1 */
  420.             /* the width of the picture in pixels    /* 1 */
  421.             /* (mhd.w) times the number of bytes of    /* 1 */
  422.             /* data supplyed per pixel (0.5 for    /* 1 */
  423.             /* B&W, 1.5 for color). This is so that    /* 1 */
  424.             /* every time the "image" command    /* 1 */
  425.             /* invokes the reading procedure, all    /* 1 */
  426.             /* N bytes representing one scan line    /* 1 */
  427.             /* are read.                /* 1 */
  428.     fprintf(fout,"/picstr %d string def\r",
  429.         (int)(width * (blacknwhite ? 0.5 : 1.5)));    /* 1 */
  430.     fprintf(fout,"%ld %ld translate\r",x1,y1);
  431.     if(rotate)                        /* 1 */
  432.         fprintf(fout, "%d rotate\r", rotate);        /* 1 */
  433.     fprintf(fout,"%ld %ld scale\r",x2,y2);
  434.     fprintf(fout, "%d %d 4 [%d 0 0 -%d 0 %d]\r",
  435.         width, height, width, height, height);        /* 1 */
  436.     fprintf(fout,"{currentfile picstr readhexstring pop}");
  437. #ifdef QMS                            /* 1 */
  438.     if(blacknwhite == FALSE)                /* 1 */
  439.         fprintf(fout, " false 3 colorimage\r");        /* 1 */
  440.     else                    /* color! */    /* 1 */
  441. #endif QMS                            /* 1 */
  442.     fprintf(fout, " image\r");
  443.  
  444.             /* calculate and output file */
  445.  
  446.     lb = lr = lg = 0;
  447.     printf("rast size : %d     #planes : %d\n",
  448.                 mhd.w*mhd.h/8, mhd.npl);    /* 1 */
  449.             /* what does this do?            */
  450.     for (h=0; h<96; h++)
  451.         cmap[h] = cmap[h]/16;
  452.     for (h=0; h<mhd.h; h++) {
  453.         for (i=0; i<mhd.w/8; i++) {
  454.             for(k=7;k>=0;k--) {
  455.                 b=0;
  456.                 for(j=0; j<mhd.npl; j++) {
  457.                     c = (raster[h*(mhd.w/8)*mhd.npl+i+((mhd.npl-j-1)*mhd.w/8)]);
  458.                     c = c>>k;
  459.                     c &= 1;
  460.                     b |= c;
  461.                     b <<= 1;
  462.                 }
  463.                 b >>= 1;
  464.  
  465.                     /* this is for HAM pictures */
  466.                 if (mhd.npl == 6) {
  467.                     c = (b&48) >> 4;
  468.                     b &= 15;
  469.                     if (c == 0) {
  470.                         b *= 3;
  471.                         lr = cmap[b];
  472.                         lb = cmap[b+1];
  473.                         lg = cmap[b+2];
  474.                     }
  475.                     if (c == 1) lb = b;
  476.                     if (c == 2) lr = b;
  477.                     if (c == 3) lg = b;
  478.                 }
  479.                 if (mhd.npl != 6) {
  480.                     b &= 31;
  481.                     b *= 3;
  482.                     lr = cmap[b];
  483.                     lb = cmap[b+1];
  484.                     lg = cmap[b+2];
  485.                 }
  486.                 if(blacknwhite){        /* 1 */
  487.                     m = lr+lb+lg; m = m/3;
  488.                     if (m < 0) m = 0;
  489.                     if (m > 14) m = 14;
  490. #ifdef SMOOTH_INCLUDE                        /* 1 */
  491.                     putval1(m, fout, h,    /* 1 */
  492.                         (i*8) + (7-k));    /* 1 */
  493. #else SMOOTH_INCLUDE                        /* 1 */
  494.                     putc(hex[m], fout);
  495. #endif SMOOTH_INCLUDE                        /* 1 */
  496.                 }                /* 1 */
  497.                 else{        /* color! */    /* 1 */
  498. #ifdef SMOOTH_INCLUDE                        /* 1 */
  499.                     putval2(lr,lg,lb,fout,    /* 1 */
  500.                         h,(i*8)+(7-k));    /* 1 */
  501. #else SMOOTH_INCLUDE                        /* 1 */
  502.                     putc(hex[lr], fout);
  503.                     putc(hex[lg], fout);
  504.                     putc(hex[lb], fout);
  505. #endif SMOOTH_INCLUDE                        /* 1 */
  506.                 }                /* 1 */
  507.             }
  508.         }
  509.     }        /* end of map-header-count FOR loop    */
  510.  
  511.     fprintf(fout,"\r");
  512.     if(showpage)                        /* 1 */
  513.         fprintf(fout,"showpage\r");
  514.  
  515.     fclose(fout);
  516.     printf("Done !!!\n");
  517.     free(misc);
  518.     free(raster);
  519. #ifdef DEBUG                            /* 1 */
  520. printf("\n\tmhd.w = %d    mhd.h = %d\n", mhd.w, mhd.h);        /*999*/
  521. printf("\twidth = %d    height = %d\n", width, height);        /*999*/
  522. #endif DEBUG                            /* 1 */
  523. }
  524.  
  525.  
  526. #ifdef SMOOTH_INCLUDE                        /* 1 */
  527. void                                /* 1 */
  528. putval1(pixelval, fout, rownum, pixelnum)            /* 1 */
  529.     char pixelval;        /* the binary value */        /* 1 */
  530.     int rownum, pixelnum;
  531.     FILE *fout;{
  532.     int i;
  533.     char tempval;
  534.  
  535.             /* NOTE: the raw values are placed in    */
  536.             /* the odd numbered elements of the    */
  537.             /* arrays and the averaged values are    */
  538.             /* placed in the even numbered elements.*/
  539.             /* The exception to this is the zeroth    */
  540.             /* pixels and row. Since these values    */
  541.             /* cannot be produced (because there is    */
  542.             /* no previous value to average with)    */
  543.             /* they are initialized with the value    */
  544.             /* of the zeroth pixel (which also    */
  545.             /* exists in array element numbered "1")*/
  546.     if(smooth){
  547.         if(rownum == 0){
  548.             if(pixelnum == 0){
  549.                 smoothrow[0] = pixelval;
  550.                 smoothrow[1] = pixelval;
  551.                 pixelrow[0] = pixelval;
  552.                 pixelrow[1] = pixelval;
  553.             }
  554.             else{
  555.                 smoothrow[(2*pixelnum)+1] =
  556.                             pixelval;
  557.                 pixelrow[(2*pixelnum)+1] =
  558.                             pixelval;
  559.     
  560.                 tempval =
  561.                 (pixelrow[(2*pixelnum)-1] +
  562.                     pixelval) / 2;
  563.                 smoothrow[2*pixelnum] = tempval;
  564.                 pixelrow[2*pixelnum] = tempval;
  565.             }
  566.         }
  567.         else{        /* rownum != 0    */
  568.             if(pixelnum == 0){
  569.                 smoothrow[1] =
  570.                 (pixelrow[1] + pixelval) / 2;
  571.                 pixelrow[1] = pixelval;
  572.                 smoothrow[0] = smoothrow[1];
  573.                 pixelrow[0] = pixelval;
  574.             }
  575.             else{
  576.                 smoothrow[(2*pixelnum)+1] =
  577.                 (pixelrow[(2*pixelnum)+1] +
  578.                     pixelval) / 2;
  579.     
  580.                 pixelrow[(2*pixelnum)+1] =
  581.                             pixelval;
  582.     
  583.                 tempval =
  584.                 (pixelrow[(2*pixelnum)-1] +
  585.                     pixelval) / 2;
  586.                 smoothrow[2*pixelnum] =
  587.                 (pixelrow[2*pixelnum] +
  588.                     tempval) / 2;
  589.     
  590.                 pixelrow[2*pixelnum] = tempval;
  591.             }
  592.         }
  593.  
  594.             /* if the last pixel in the row has    */
  595.             /* been processed then write the two    */
  596.             /* rows to the output file.        */
  597.         if(pixelnum == ((width/2) - 1)){
  598.             for(i=0; i < width; i++)
  599.                 putc(hex[smoothrow[i]], fout);
  600.             for(i=0; i < width; i++)
  601.                 putc(hex[pixelrow[i]], fout);
  602.         }
  603.     }
  604.     else                /* no smoothing    */
  605.         putc(hex[pixelval], fout);
  606. }
  607.  
  608.  
  609. #define SETPIXELS(array,index,r,g,b)            /* 1 */\
  610.         array[(3*index)+0] = r;            /* 1 */\
  611.         array[(3*index)+1] = g;            /* 1 */\
  612.         array[(3*index)+2] = b;            /* 1 */
  613.  
  614. #define AVE0PIX(array,index,val)            /* 1 */\
  615.         ((array[(3*index)+0]+val)/2)
  616. #define AVE1PIX(array,index,val)            /* 1 */\
  617.         ((array[(3*index)+1]+val)/2)
  618. #define AVE2PIX(array,index,val)            /* 1 */\
  619.         ((array[(3*index)+2]+val)/2)
  620.  
  621. void                                /* 1 */
  622. putval2(redval, greenval, blueval, fout, rownum, pixelnum)    /* 1 */
  623.     char redval, greenval, blueval;    /* the binary value */    /* 1 */
  624.     int rownum, pixelnum;
  625.     FILE *fout;{
  626.     int i;
  627.     char tempred, tempgreen, tempblue;
  628.  
  629.             /* NOTE: the raw values are placed in    */
  630.             /* the odd numbered elements of the    */
  631.             /* arrays and the averaged values are    */
  632.             /* placed in the even numbered elements.*/
  633.             /* The exception to this is the zeroth    */
  634.             /* pixels and row. Since these values    */
  635.             /* cannot be produced (because there is    */
  636.             /* no previous value to average with)    */
  637.             /* they are initialized with the value    */
  638.             /* of the zeroth pixel (which also    */
  639.             /* exists in array element numbered "1")*/
  640.     if(smooth){
  641.         if(rownum == 0){
  642.             if(pixelnum == 0){
  643.                 SETPIXELS(smoothrow,0,redval,
  644.                         greenval,blueval)
  645.                 SETPIXELS(smoothrow,1,redval,
  646.                         greenval,blueval)
  647.                 SETPIXELS(pixelrow,0,redval,
  648.                         greenval,blueval)
  649.                 SETPIXELS(pixelrow,1,redval,
  650.                         greenval,blueval)
  651.             }
  652.             else{
  653.                     /* store raw values    */
  654.                 SETPIXELS(smoothrow,((2*pixelnum)+1),
  655.                     redval,greenval,blueval)
  656.                 SETPIXELS(pixelrow,((2*pixelnum)+1),
  657.                     redval,greenval,blueval)
  658.     
  659.                     /* calculate and store    */
  660.                     /* averaged values    */
  661.                 tempred =
  662.                 (pixelrow[(3*((2*pixelnum)-1))+0] +
  663.                     redval) / 2;
  664.                 tempgreen =
  665.                 (pixelrow[(3*((2*pixelnum)-1))+1] +
  666.                     greenval) / 2;
  667.                 tempblue =
  668.                 (pixelrow[(3*((2*pixelnum)-1))+2] +
  669.                     blueval) / 2;
  670.                 SETPIXELS(smoothrow,(2*pixelnum),
  671.                     tempred,tempgreen,tempblue)
  672.                 SETPIXELS(pixelrow,(2*pixelnum),
  673.                     tempred,tempgreen,tempblue)
  674.             }
  675.         }
  676.         else{        /* rownum != 0    */
  677.             if(pixelnum == 0){
  678.                 SETPIXELS(smoothrow,1,
  679.                     AVE0PIX(pixelrow,1,redval),
  680.                     AVE1PIX(pixelrow,1,greenval),
  681.                     AVE2PIX(pixelrow,1,blueval))
  682.                 SETPIXELS(pixelrow,1,redval,
  683.                         greenval,blueval)
  684.                 SETPIXELS(smoothrow,0,smoothrow[3],
  685.                     smoothrow[4],smoothrow[5])
  686.                 SETPIXELS(pixelrow,0,redval,
  687.                         greenval,blueval)
  688.             }
  689.             else{
  690.                 SETPIXELS(smoothrow,((2*pixelnum)+1),
  691.             AVE0PIX(pixelrow,((2*pixelnum)+1),redval),
  692.             AVE1PIX(pixelrow,((2*pixelnum)+1),greenval),
  693.             AVE2PIX(pixelrow,((2*pixelnum)+1),blueval))
  694. /*
  695.                 smoothrow[(2*pixelnum)+1] =
  696.                 (pixelrow[(2*pixelnum)+1] +
  697.                     pixelval) / 2;
  698. */
  699.     
  700.                 SETPIXELS(pixelrow,((2*pixelnum)+1),
  701.                     redval,greenval,blueval)
  702.     
  703.                     /* calculate and store    */
  704.                     /* averaged values    */
  705.                 tempred =
  706.                 (pixelrow[(3*((2*pixelnum)-1))+0] +
  707.                     redval) / 2;
  708.                 tempgreen =
  709.                 (pixelrow[(3*((2*pixelnum)-1))+1] +
  710.                     greenval) / 2;
  711.                 tempblue =
  712.                 (pixelrow[(3*((2*pixelnum)-1))+2] +
  713.                     blueval) / 2;
  714.                 SETPIXELS(smoothrow,(2*pixelnum),
  715.             AVE0PIX(pixelrow,(2*pixelnum),tempred),
  716.             AVE1PIX(pixelrow,(2*pixelnum),tempgreen),
  717.             AVE2PIX(pixelrow,(2*pixelnum),tempblue))
  718. /*
  719.                 smoothrow[2*pixelnum] =
  720.                 (pixelrow[2*pixelnum] +
  721.                     tempval) / 2;
  722. */
  723.     
  724.                 SETPIXELS(pixelrow,(2*pixelnum),
  725.                     tempred,tempgreen,tempblue)
  726.             }
  727.         }
  728.  
  729.             /* if the last pixel in the row has    */
  730.             /* been processed then write the two    */
  731.             /* rows to the output file.        */
  732.         if(pixelnum == ((width/2) - 1)){
  733.             for(i=0; i < width; i++){
  734.                 putc(hex[smoothrow[(3*i)+0]], fout);
  735.                 putc(hex[smoothrow[(3*i)+1]], fout);
  736.                 putc(hex[smoothrow[(3*i)+2]], fout);
  737.             }
  738.             for(i=0; i < width; i++){
  739.                 putc(hex[pixelrow[(3*i)+0]], fout);
  740.                 putc(hex[pixelrow[(3*i)+1]], fout);
  741.                 putc(hex[pixelrow[(3*i)+2]], fout);
  742.             }
  743.         }
  744.     }
  745.     else{                /* no smoothing    */
  746.         putc(hex[redval], fout);
  747.         putc(hex[greenval], fout);
  748.         putc(hex[blueval], fout);
  749.     }
  750. }
  751. #endif SMOOTH_INCLUDE                        /* 1 */
  752.