/*********************************************************************/
#include <exec/types.h>
#include <exec/nodes.h>
#include <exec/lists.h>
#include <exec/memory.h>
#include <devices/printer.h>
#include <devices/prtbase.h>

extern struct PrinterData *PD;
extern struct PrinterExtendedData *PED;

/* for the EPSONJX-80 */
int Render(ct, x, y, status)
   UBYTE ct;   /* color code */
   UWORD x, y;   /* the x & y co-ordinates */
         /* or the pc & pr print values, or special */
   UBYTE status;   /* print status (0-init, 1-enter pixel, 2-dump) */
{
   static UWORD ROWSIZE;
   static UWORD COLORSIZE;
   static UWORD BUFSIZE;
   static UWORD colors[4]; /* color ptrs */
   static BYTE spacing, center, colorcodes[4] = {4, 1, 2, 0}; /* the color codes */
   static UWORD bufptr; /* used for double buffering */
   static UBYTE *ptr, bit_table[] = {128, 64, 32, 16, 8, 4, 2, 1};
   UWORD i;               /* mics. var */
   BYTE err;            /* the error # */

   switch(status)
   {
   case 0 :   /* alloc memory for printer buffer */
      i = (center) ? ((PED->ped_MaxXDots - x) / 2) : 0;
      ROWSIZE=x+i;   /* row size required for EPSON JX-80 */
      COLORSIZE=(ROWSIZE+8); /* size of each color buffer */
      BUFSIZE=(COLORSIZE*4+1);   /* buffer size required for EPSON JX-80 */
      colors[0] = COLORSIZE*3+7 + i;
      colors[1] = 7 + i;
      colors[2] = COLORSIZE+7 + i;
      colors[3] = COLORSIZE*2+7 + i;
      PD->pd_PrintBuf = (UBYTE *)
         AllocMem(BUFSIZE*2,MEMF_PUBLIC); /* alloc public mem */
      if (err=(PD->pd_PrintBuf == 0)) return(int)(err);
      if (err=(*(PD->pd_PWrite))("\033@",2)) return(int)(err); /* reset to power-up state */
      if (err=PWait(3,0)) return(int)(err);
/* special epson spacing code */
   if (spacing==7) {
      if (err=(*(PD->pd_PWrite))("\0331",2)) return(int)(err); /* select 7/72 inch \
spacing */
   }
   else {
      if (err=(*(PD->pd_PWrite))("\0333\030",3)) return(int)(err); /* select 24/216\
 (8/72) inch spacing */
   }
/* end of special epson spacing code */
      if (err=(*(PD->pd_PWrite))("\033U1",3)) return(int)(err); /* set unidirec mode */
      bufptr=0; /* init to first buffer */
      return(0); /* flag all ok */
      break;

   case 1 :   /* put pixel in buffer */
/*      i = bufptr+x+colors[ct];   /* calc which byte to use */
/*      PD->pd_PrintBuf[i] = PD->pd_PrintBuf[i] | (1 << (7-(y&7))); /* fill print buffer */
      PD->pd_PrintBuf[bufptr+x+colors[ct]] |= bit_table[y&7];
      return(0); /* flag all ok */
      break;

   case 2 : /* dump buffer to printer */
      if (err=(*(PD->pd_PWrite))(&(PD->pd_PrintBuf[bufptr]), BUFSIZE)) return(int)(err);
      bufptr=BUFSIZE-bufptr; /* switch to other buffer */
      return(0); /* flag all ok */
      break;

   case 3 : /* clear and init buffer */
/*      for (i=bufptr; i<bufptr+BUFSIZE; i++)
         PD->pd_PrintBuf[i] = 0;   /* clear buffer */
      ptr = &PD->pd_PrintBuf[bufptr];
      i = BUFSIZE;
      while (i--) *ptr++ = 0;
      for (ct=0; ct<4; ct++) {
         PD->pd_PrintBuf[bufptr+ct*COLORSIZE] = 27;
         PD->pd_PrintBuf[bufptr+1+ct*COLORSIZE] = 'r';
         PD->pd_PrintBuf[bufptr+2+ct*COLORSIZE] = colorcodes[ct]; /* select color */
         PD->pd_PrintBuf[bufptr+3+ct*COLORSIZE] = 27;
         PD->pd_PrintBuf[bufptr+4+ct*COLORSIZE] = 'L';
         PD->pd_PrintBuf[bufptr+5+ct*COLORSIZE] = ROWSIZE & 0xff;
         PD->pd_PrintBuf[bufptr+6+ct*COLORSIZE] = ROWSIZE >> 8; /* 960 dot mode */
         PD->pd_PrintBuf[bufptr+7+ROWSIZE+ct*COLORSIZE] = 13; /* cr */
      }
      PD->pd_PrintBuf[bufptr+BUFSIZE-1] = 10; /* lf */
      return(0); /* flag all ok */
      break;

   case 4 : /* free the print buffer memory */
      err=(*(PD->pd_PWrite))("\033@",2); /* reset printer to power-up state */
      if (!err) err=(*(PD->pd_PBothReady))(); /* wait for both buffers to clear */
      FreeMem(PD->pd_PrintBuf,BUFSIZE*2); /* free memory */
      return(int)(err); /* return status */
      break;

   case 5 : /* io_special flag call */
      center = x & SPECIAL_CENTER; /* set center flag */
/* special code for epson spacing */
      if (PD->pd_Preferences.PaperSize==CUSTOM) { /* if want 7/72 spacing */
         PED->ped_YDotsInch = (UWORD)82; /* (72/7*8 gives 82.3) there are 82 d\
pi in y */
         spacing = 7; /* 7/72 inch spacing */
      }
      else { /* else use default of 8/72 spacing */
         PED->ped_YDotsInch = (UWORD)72; /* (72/8*8 gives 72) there are 72 dpi\
 in y */
         spacing = 8; /* 8/72 inch spacing */
      }
      return(0); /* flag all ok */
      break;

   default: return(0);
   }
}
/*********************************************************************/
