home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / netpbma.zip / pbm / pbmtolps.c < prev    next >
C/C++ Source or Header  |  1993-10-06  |  5KB  |  182 lines

  1. /*
  2.  * pbmtolps -- convert a Portable BitMap into Postscript.  The
  3.  * output Postscript uses lines instead of the image operator to
  4.  * generate a (device dependent) picture which will be imaged
  5.  * much faster.
  6.  *
  7.  * The Postscript path length is constrained to be less that 1000
  8.  * points so that no limits are overrun on the Apple Laserwriter
  9.  * and (presumably) no other printers.
  10.  *
  11.  * To do:
  12.  *      make sure encapsulated format is correct
  13.  *      repitition of black-white strips
  14.  *      make it more device independent (is this possible?)
  15.  *
  16.  * Author:
  17.  *      George Phillips <phillips@cs.ubc.ca>
  18.  *      Department of Computer Science
  19.  *      University of British Columbia
  20.  */
  21.  
  22. #include <stdio.h>
  23. #include "pbm.h"
  24.  
  25. /* prototypes */
  26. void addstrip ARGS((int white, int black));
  27. void nextline ARGS((void));
  28. char morepoints ARGS((char cmd, int howmany_pbmtolps));
  29.  
  30.  
  31. int
  32. main(argc, argv)
  33. int             argc;
  34. char*   argv[];
  35. {
  36.         FILE*   fp;
  37.         bit*    bits;
  38.         int             row;
  39.         int             col;
  40.     int         rows;
  41.         int             cols;
  42.         int             format;
  43.         int             white;
  44.         int             black;
  45.         char*   name;
  46.         float   dpi = 300.0;
  47.         float   sc_rows;
  48.         float   sc_cols;
  49.         int             i;
  50.         char*   usage = "[ -dpi n ] [ pbmfile ]";
  51.  
  52.  
  53.     pbm_init(&argc, argv);
  54.  
  55.         i = 1;
  56.         if (i < argc && !strcmp(argv[i], "-dpi")) {
  57.                 if (i == argc - 1)
  58.                         pm_usage(usage);
  59.                 sscanf(argv[i + 1], "%f", &dpi);
  60.                 i += 2;
  61.         }
  62.  
  63.         if (i < argc - 1)
  64.                 pm_usage(usage);
  65.  
  66.         if (i == argc) {
  67.                 fp = stdin;
  68.                 name = "noname";
  69.         }
  70.         else
  71.                 fp = pm_openr(name = argv[i]);
  72.  
  73.         pbm_readpbminit(fp, &cols, &rows, &format);
  74.         bits = pbm_allocrow(cols);
  75.  
  76.         sc_rows = (float)rows / dpi * 72.0;
  77.         sc_cols = (float)cols / dpi * 72.0;
  78.  
  79.         puts("%!PS-Adobe-2.0 EPSF-2.0");
  80.         puts("%%Creator: pbmtolps");
  81.         printf("%%%%Title: %s\n", name);
  82.         printf("%%%%BoundingBox: %d %d %d %d\n",
  83.                 (int)(305.5 - sc_cols / 2.0),
  84.                 (int)(395.5 - sc_rows / 2.0),
  85.                 (int)(306.5 + sc_cols / 2.0),
  86.                 (int)(396.5 + sc_rows / 2.0));
  87.         puts("%%EndComments");
  88.         puts("%%EndProlog");
  89.         puts("gsave");
  90.  
  91.         printf("%f %f translate\n", 306.0 - sc_cols / 2.0, 396.0 + sc_rows / 2.0);
  92.         printf("72 %f div dup neg scale\n", dpi);
  93.         puts("/a { 0 rmoveto 0 rlineto } def");
  94.         puts("/b { 0 row 1 add dup /row exch def moveto } def");
  95.         puts("/c { a b } def");
  96.         puts("/m { currentpoint stroke newpath moveto a } def");
  97.         puts("/n { currentpoint stroke newpath moveto b } def");
  98.         puts("/o { currentpoint stroke newpath moveto c } def");
  99.         puts("/row 0 def");
  100.         puts("newpath 0 0 moveto");
  101.  
  102.         for (row = 0; row < rows; row++) {
  103.                 pbm_readpbmrow(fp, bits, cols, format);
  104.                 /* output white-strip+black-strip sequences */
  105.                 for (col = 0; col < cols; ) {
  106.                         for (white = 0; col < cols && bits[col] == PBM_WHITE; col++)
  107.                                 white++;
  108.                         for (black = 0; col < cols && bits[col] == PBM_BLACK; col++)
  109.                                 black++;
  110.  
  111.                         if (black != 0)
  112.                                 addstrip(white, black);
  113.                 }
  114.                 nextline();
  115.         }
  116.         puts("stroke grestore showpage");
  117.         puts("%%Trailer");
  118.  
  119.     pm_close(fp);
  120.  
  121.         exit(0);
  122. }
  123.  
  124. static int prev_white = -1;
  125. static int prev_black = -1;
  126. static char cmd = '\0';
  127. static int run = 1;
  128.  
  129. void addstrip(white, black)
  130. int white;
  131. int black;
  132. {
  133.         if (cmd) {
  134. #ifdef RUN
  135.                 if (white == prev_white && black == prev_black)
  136.                         run++;
  137.                 else {
  138.                         if (run == 1)
  139. #endif
  140.                                 printf("%d %d %c ", prev_black, prev_white, morepoints(cmd, 2));
  141. #ifdef RUN
  142.                         else
  143.                                 /* of course, we need to give a new command */
  144.                                 printf("%d %d %d %c ",
  145.                                         prev_white, prev_black, run,
  146.                                         morepoints(cmd + 'f' - 'a', 2 * run));
  147.                         run = 1;
  148.                 }
  149. #endif
  150.         }
  151.  
  152.         prev_white = white;
  153.         prev_black = black;
  154.         cmd = 'a';
  155. }
  156.  
  157. void nextline()
  158. {
  159.         /* need to check run, should have an outcommand */
  160.         if (cmd)
  161.                 printf("%d %d %c\n", prev_black, prev_white, morepoints('c', 3));
  162.         else
  163.                 printf("%c\n", morepoints('b', 1));
  164.         cmd = '\0';
  165. }
  166.  
  167. static int pointcount = 2;
  168.  
  169. char morepoints(cmd, howmany_pbmtolps)
  170.     char cmd;
  171.     int howmany_pbmtolps;
  172. {
  173.         pointcount += 2;
  174.         if (pointcount > 1000) {
  175.                 pointcount = 2;
  176.                 cmd += 'm' - 'a';
  177.         }
  178.         return(cmd);
  179. }
  180.  
  181.  
  182.