home *** CD-ROM | disk | FTP | other *** search
/ Programmer 7500 / MAX_PROGRAMMERS.iso / INFO / NCSATELN / TEL23SRC.ZIP / RG / RGEP.C < prev    next >
Encoding:
C/C++ Source or Header  |  1991-06-25  |  7.0 KB  |  376 lines

  1. /*
  2. *
  3. *  rgep.c by Aaron Contorer for NCSA
  4. *
  5. *  graphics routines for drawing on Epson printer
  6. *  Input coordinate space = 0..4095 by 0..4095
  7. *  MUST BE COMPILED WITH LARGE MEMORY MODEL!
  8. *
  9. */
  10.  
  11. #include <stdio.h>    /* used for debugging only */
  12. #include <stdlib.h>
  13. #ifdef MSC
  14. #ifdef __TURBOC__
  15. #include <alloc.h>
  16. #else
  17. #include <malloc.h>
  18. #endif
  19. #endif
  20. #ifdef MEMORY_DEBUG
  21. #include "memdebug.h"
  22. #endif
  23. #include "externs.h"
  24.  
  25. #define TRUE 1
  26. #define FALSE 0
  27. #define INXMAX 4096
  28. #define INYMAX 4096
  29. #define SCRNXHI 719
  30. #define ROWS 90
  31. #define SCRNYHI 929
  32. #define LINEBYTE 930
  33. #define MAXRW 1        /* max. number of real windows */
  34.  
  35. static int EPSactive; /* number of currently active window */
  36. static char EPSpbit[SCRNXHI+1];
  37. static unsigned char power2[8]={1,2,4,8,16,32,64,128};
  38. static char *EPSname="Epson, IBM, or compatible printer";
  39. static int EPSxmax=720;
  40. static int EPSymax=LINEBYTE;
  41. static int EPSbytes=80;    /* number of bytes per line */
  42. static unsigned char *EPSram[ROWS];
  43. static void (*EPSoutfunc)(char c);
  44. static void signore(char c);
  45. static void EPSpoint(int x,int y);
  46. static void EPSdump(void );
  47. static void EPSsetup(void );
  48.  
  49. /* Current status of an EPS window */
  50. struct EPSWIN 
  51. {
  52.     char inuse; /* true if window in use */
  53.     int pencolor, rotation, size;
  54.     int winbot,winleft,wintall,winwide;
  55.         /* position of the window in virtual space */
  56. };
  57.  
  58. static struct EPSWIN EPSwins[MAXRW];
  59.  
  60. static void EPSsetup(void )
  61. /* prepare variables for use in other functions */
  62. {
  63.     int x;
  64.     EPSpbit[0]=128; 
  65.     EPSpbit[1]=64; 
  66.     EPSpbit[2]=32; 
  67.     EPSpbit[3]=16;
  68.     EPSpbit[4]=8;   
  69.     EPSpbit[5]=4;  
  70.     EPSpbit[6]=2;  
  71.     EPSpbit[7]=1;
  72.     for(x=8; x<=SCRNXHI; x++) 
  73.         EPSpbit[x]=EPSpbit[x&7];
  74. }
  75.  
  76. void RGEPgmode()                /* go into EPS graphics mode */
  77. {
  78. }
  79.  
  80. void RGEPtmode()                /* go into EPS text mode */
  81. {
  82. }
  83.  
  84. void RGEPclrscr(w)
  85. int w;
  86. /* 
  87.     Clear the screen.
  88. */
  89. {
  90.     if(w==EPSactive)
  91.         EPSsetup();
  92. }
  93.  
  94. int RGEPnewwin()
  95. /* 
  96.     Set up a new window; return its number.
  97.     Returns -1 if cannot create window.
  98. */
  99. {
  100.     int w=0;
  101.     int x,y;
  102.     for(x=0; x<ROWS; x++) {
  103.         if((EPSram[x]=malloc(LINEBYTE))==NULL) {    /* ran out of memory, free what we have now */
  104.             for(; x>=0; x--)
  105.                 free(EPSram[x]);
  106.             return(-1);
  107.           }    /* end if */
  108.         for(y=0; y<LINEBYTE; y++) 
  109.             (EPSram[x])[y]=0;
  110.       }
  111.     while(w<MAXRW&&EPSwins[w].inuse) 
  112.         w++;
  113.     if(w==MAXRW) 
  114.         return(-1); /* no windows available */
  115.     EPSwins[w].pencolor=7;
  116.     EPSwins[w].winbot=0;
  117.     EPSwins[w].wintall=3120;
  118.     EPSwins[w].winleft=0;
  119.     EPSwins[w].winwide=4096;
  120.     EPSwins[w].inuse=TRUE;
  121.     return(w);
  122. }
  123.  
  124. void RGEPclose(w)
  125. int w;
  126. {
  127.     if(EPSactive==w) {
  128.         RGEPclrscr(w);
  129.         EPSactive=-1;
  130.       }
  131.     EPSdump();
  132.     EPSwins[w].inuse=FALSE;
  133. }
  134.  
  135. void RGEPpoint(w,x,y)
  136. int w,x,y;
  137. /* set pixel at location (x,y) -- no range checking performed */
  138. {
  139.     int x2,y2;             /* on-screen coordinates */
  140.  
  141.     if(w==EPSactive) {
  142.         x2=(int)((long)x*EPSxmax/INXMAX);
  143.         y2=(int)((long)y*EPSymax/INYMAX);
  144.         EPSpoint(x2,y2);
  145.       }
  146. }  
  147.  
  148. void RGEPpagedone(w)
  149. int w;
  150. /*
  151.     Do whatever has to be done when the drawing is all done.
  152.     (For printers, that means eject page.)
  153. */
  154. {
  155.     EPSdump();
  156.     w=w;
  157. }
  158.  
  159. void RGEPdataline(w,data,count)
  160. int w,count;
  161. char *data;
  162. /*
  163.     Copy 'count' bytes of data to screen starting at current
  164.     cursor location.
  165. */
  166. {
  167.     /* Function not supported yet. */
  168.     w=w;
  169.     data=data;
  170.     count=count;
  171. }
  172.  
  173. void RGEPpencolor(w,color)
  174. int w,color;
  175. /*
  176.     Change pen color to the specified color.
  177. */
  178. {
  179.     /* Function not supported. */
  180.     w=w;
  181.     color=color;
  182. }
  183.  
  184. void RGEPcharmode(int w,int rotation,int size)
  185. /*
  186.     Set description of future device-supported graphtext.
  187.     Rotation=quadrant.
  188. */
  189. {
  190.     /* No rotatable device-supported graphtext is available on EPS. */
  191.     w=w;
  192.     rotation=rotation;
  193.     size=size;
  194. }
  195.  
  196. /* Not yet supported: */
  197. void RGEPshowcur() {}
  198. void RGEPlockcur() {}
  199. void RGEPhidecur() {}
  200.  
  201. static void EPSpoint(int x,int y)
  202. /*
  203.     Set bit at x,y
  204. */
  205. {
  206.     (EPSram[x>>3])[y]|=EPSpbit[x];
  207. }
  208.  
  209. void RGEPdrawline(w,x0,y0,x1,y1)
  210. int w,x0,y0,x1,y1;
  211. /* draw a line from (x0,y0) to (x1,y1) */
  212. /* uses Bresenham's Line Algorithm */
  213. {
  214.     int x,y,dx,dy,d,temp,
  215.     dx2,dy2,        /* 2dx and 2dy */
  216.     direction;        /* +1 or -1, used for slope */
  217.     char transpose;    /* true if switching x and y for vertical-ish line */
  218.  
  219.     if(w!=EPSactive) 
  220.         return;
  221.     x0=(int)((long)x0*EPSxmax/INXMAX);
  222.     y0=(int)((long)y0*EPSymax/INYMAX);
  223.     x1=(int)((long)x1*EPSxmax/INXMAX);
  224.     y1=(int)((long)y1*EPSymax/INYMAX);
  225.  
  226.     if(abs(y1-y0)>abs(x1-x0)) {            /* transpose vertical-ish to horizontal-ish */
  227.         temp=x1; 
  228.         x1=y1; 
  229.         y1=temp;
  230.         temp=x0; 
  231.         x0=y0; 
  232.         y0=temp;
  233.         transpose=TRUE;
  234.       } 
  235.     else 
  236.         transpose=FALSE;            /* make sure line is left to right */
  237.     if(x1<x0) {
  238.         temp=x1; 
  239.         x1=x0; 
  240.         x0=temp; 
  241.         temp=y1; 
  242.         y1=y0; 
  243.         y0=temp;
  244.       }
  245.                                     /* SPECIAL CASE: 1 POINT */
  246.     if(x1==x0&&y1==y0) { 
  247.         EPSpoint(x1,y1);
  248.         return;
  249.       }        
  250.                                     /* ANY LINE > 1 POINT */
  251.     x=x0;
  252.     y=y0;
  253.     dx=x1-x0;
  254.     if(y1>=y0) {
  255.         dy=y1-y0;
  256.         direction=1;
  257.       } 
  258.     else {
  259.         dy=y0-y1;
  260.         direction=-1;
  261.       }
  262.     dx2=dx<<1;
  263.     dy2=dy<<1;
  264.     d=(dy<<1)-dx;
  265.     if(transpose) {        /* CASE OF VERTICALISH (TRANSPOSED) LINES */
  266.         while(x<=x1) {
  267.             if(y>=0&&y<EPSxmax&&x>=0&&x<EPSymax)
  268.                 EPSpoint(y,x);
  269.             while(d>=0) {
  270.                 y+=direction;
  271.                 d-=dx2;
  272.               }
  273.             d+=dy2;
  274.             x++;
  275.           } 
  276.       } 
  277.     else {                /* CASE OF HORIZONTALISH LINES */
  278.         while(x<=x1) {
  279.             if(x>=0&&x<EPSxmax&&y>=0&&y<EPSymax)
  280.                 EPSpoint(x,y);
  281.             while(d>=0){
  282.                 y+=direction;
  283.                 d-=dx2;
  284.               }
  285.             d+=dy2;
  286.             x++;
  287.           }
  288.       }                 /* end horizontalish */
  289. }                         /* end RGEPdrawline() */
  290.  
  291. void RGEPbell(w)
  292. int w;                    /* Ring bell in window w */
  293. {
  294.     w=w;
  295. }
  296.  
  297. char *RGEPdevname()        /* return name of device that this RG supports */
  298. {
  299.     return(EPSname);
  300. }
  301.  
  302. static void signore(s)
  303. char s;
  304. /* Ignore the character pointer passed here. */
  305. {
  306.     s=s;
  307. }
  308.  
  309. void RGEPinit()
  310. /* initialize all RGEP variables */
  311. {
  312.     int i;
  313.     EPSsetup();
  314.     for(i=0; i<MAXRW; i++) 
  315.         EPSwins[i].inuse=FALSE;
  316.     EPSactive=-1;
  317.     EPSoutfunc=signore;
  318. }
  319.  
  320. void RGEPoutfunc(f)
  321. void (*f)(char );
  322. /*
  323.     Specify the function that is to be called with pointers to all
  324.     the printout strings.
  325. */
  326. {
  327.     EPSoutfunc=f;
  328. }
  329.  
  330. void RGEPuncover(w)
  331. int w;
  332. /*
  333.     Make this window visible, hiding all others.
  334.     Caller should follow this with clrscr and redraw to show the current
  335.     contents of the window.
  336. */
  337. {
  338.     EPSactive=w;
  339. }
  340.  
  341. void RGEPinfo(int w,int a,int b,int c,int d,int v) {
  342.     
  343. /* Needed for possible future functionality */
  344.  
  345.     w=w;
  346.     a=a;
  347.     b=b;
  348.     c=c;
  349.     d=d;
  350.     v=v;
  351.     }
  352.  
  353. static void EPSdump(void )
  354. /*
  355. *    Dump the contents of the buffer to the specified function.
  356. */
  357. {
  358.     int x,y;
  359.     int size=EPSymax*2;
  360.  
  361.     for(x=0;x<90;x++) {                /* init graphics mode */
  362.         (*EPSoutfunc)(033);
  363.         (*EPSoutfunc)('L');
  364.         (*EPSoutfunc)((char)(size&255));
  365.         (*EPSoutfunc)((char)(size>>8));        /* send a line of bit image data */
  366.         for(y=0; y<size; y++) 
  367.             (*EPSoutfunc)((EPSram[x]) [y]);
  368.                                     /* go to next line */
  369.         (*EPSoutfunc)(13);
  370.         (*EPSoutfunc)(033);
  371.         (*EPSoutfunc)('J');
  372.         (*EPSoutfunc)(24);
  373.       }
  374.     (*EPSoutfunc)(12); /* form feed */
  375. }
  376.