diff options
Diffstat (limited to 'Build/source/texk/web2c/window/hp2627.c')
-rw-r--r-- | Build/source/texk/web2c/window/hp2627.c | 252 |
1 files changed, 252 insertions, 0 deletions
diff --git a/Build/source/texk/web2c/window/hp2627.c b/Build/source/texk/web2c/window/hp2627.c new file mode 100644 index 00000000000..2734bb36a02 --- /dev/null +++ b/Build/source/texk/web2c/window/hp2627.c @@ -0,0 +1,252 @@ +/* + * HP2627 Terminal Window interface to Unix Metafont. + */ + +#define EXTERN extern +#include "../mfd.h" + +#ifdef HP2627WIN + +#include <stdio.h> + +/* + * HP2627a Color Graphics Terminal: Escape code definitions + * + * Drawing pen colors + */ +#define HP2627_BLACK '0' +#define HP2627_RED '1' +#define HP2627_GREEN '2' +#define HP2627_YELLOW '3' +#define HP2627_BLUE '4' +#define HP2627_MAGENTA '5' +#define HP2627_CYAN '6' +#define HP2627_WHITE '7' + +/* + * Initialization: just do a hard graphics reset + * (then we can depend on the defaults + * being as we want them) + */ +#define HP2627_INITSTRING "\033*wR" +#define HP2627_INITSTRINGLEN 4 + +/* + * We want the text to be visible over both background and forground + * graphics data; the best color combination I found for this + * was to set the background RED and then paint with BLUE, + * although the eye doesn't focus on BLUE very well (black + * might be better? Or green? [to get in the holiday mood]) + */ +#define HP2627_BACKGROUNDPEN HP2627_RED +#define HP2627_FOREGROUNDPEN HP2627_BLUE + +static char mf_hp2627_pencolors[2] = { + HP2627_BACKGROUNDPEN, /* white */ + HP2627_FOREGROUNDPEN /* black */ +}; + +/* + * Screen dimensions: Note the origin is at the lower-left corner, + * not the upper left as MF expects - hence we need to translate. + */ +#define HP2627_MAXX 511 +#define HP2627_MAXY 389 + +/* + * The actual Graphics routines. Note that these are highly tty + * dependent so I can minimize the number of characters that + * need to be sent to paint an image, since we only talk to + * the HP at 9.6Kb. + */ + +/* + * function init_screen: boolean; + * + * Return true if window operations legal. + * We always return true (I suppose we could try to + * sense status or something masochistic like that) + */ + +int mf_hp2627_initscreen() +{ + (void) fflush(stdout); /* make sure pascal-level output flushed */ + (void) write(fileno(stdout), HP2627_INITSTRING, HP2627_INITSTRINGLEN); + return(1); +} + +/* + * procedure updatescreen; + * + * Just make sure screen is ready to view + * (since we do Unix-level WRITE()s, + * we don't really need to flush stdio, + * but why not?) + */ + +void mf_hp2627_updatescreen() +{ + (void) fflush(stdout); +} + +/* + * procedure blankrectangle(left, right, top, bottom: integer); + * + * reset rectangle bounded by ([left,right],[top,bottom]) + * to background color + */ + +void mf_hp2627_blankrectangle P4C(screencol, left, + screencol, right, + screenrow, top, + screenrow, bottom) +{ + char sprbuf[128]; + + (void) sprintf(sprbuf, "\033*m%cx%d,%d %d,%dE", HP2627_BACKGROUNDPEN, + left, HP2627_MAXY-bottom, + right, HP2627_MAXY-top); + (void) write(fileno(stdout), sprbuf, strlen(sprbuf)); +} + +/* + * procedure paintrow( + * row: screenrow; + * init_color: pixelcolor; + * var trans_vector: transspec; + * vector_size: screencol ); + * + * Paint "row" starting with color "init_color", up to next + * transition specified by "transition_vector", switch colors, + * and continue for "vector_size" transitions. + */ + +/* + * First some useful definitions: + */ +#define ASCIILABS 0 /* plot cmd format: ASCII long abs */ +#define BINLABS 1 /* plot cmd format: BINARY long abs */ +#define BINSINC 2 /* plot cmd format: BINARY short incr */ + +#define ABS(x) ((x>=0)?x:-x) /* absolute value */ + +/* + * An optimized "move to (x,y), with current pen lowered unless UP is + * true" function. Takes advantage of short commands for short + * movements to minimize character traffic to term. + * + * Note: the "x -= 1;" fudge is because we only want to DRAW + * to the next transition_vector entry - 1, but if we + * have the pen raised, we want to move to exactly the + * next point. + */ +#define MOVETO(x,y,up) \ + if (up) *op++ = 'a'; \ + else x -= 1; \ + if (ABS(x-oldx) < 16 && ABS(y-oldy) < 16) { \ + if (currentformat != BINSINC) { \ + *op++ = 'j'; \ + currentformat = BINSINC; \ + } \ + *op++ = (((x-oldx) & 0x1f) + ' '); \ + *op++ = (((y-oldy) & 0x1f) + ' '); \ + } else { \ + if (currentformat != BINLABS) { \ + *op++ = 'i'; \ + currentformat = BINLABS; \ + } \ + *op++ = (((x&0x3e0)>>5)+' '); \ + *op++ = ((x&0x01f) +' '); \ + *op++ = (((y&0x3e0)>>5)+' '); \ + *op++ = ((y&0x01f) +' '); \ + } \ + oldx = x; \ + oldy = y; + +void mf_hp2627_paintrow P4C(screenrow, row, + pixelcolor, init_color, + transspec, transition_vector, + screencol, vector_size) +{ + register color; + char outbuf[512*6]; /* enough to hold an alternate color */ + /* in each column */ + register char *op; + register x, y, oldx, oldy; + int currentformat; + + color = (init_color == 0)? 0 : 1; + + /* + * We put all escape sequences in a buffer so the write + * has a chance of being atomic, and not interrupted by + * other independent output to our TTY. Also to avoid + * (literally millions) of stdio calls. + */ + op = outbuf; + /* + * Select current pen to be the color of the first segment: + * + * our strategy here is to paint a long line from the first + * transition_vector value (left edge of row) to the last + * transition_vector entry (right edge of row). Then we switch + * colors to the contrasting color, and paint alternate + * segments with that color. Would that the HP2627 would provide + * a mode to paint the "background" color while the PEN is lifted. + * However, this is faster than using rectangular area fills. + */ + + *op++ = '\033'; *op++ = '*'; *op++ = 'm'; + *op++ = mf_hp2627_pencolors[color]; + *op++ = 'X'; + + /* + * Reset our "remembered" state for (X,Y) positioning and plot + * command format + */ + oldx = oldy = -999; + currentformat = ASCIILABS; + + /* + * Now, paint across the entire width of this row, make it the + * initial segment color. + */ + x = *transition_vector; + y = HP2627_MAXY-row; + *op++ = '\033'; *op++ = '*'; *op++ = 'p'; + MOVETO(x,y,1); + x = transition_vector[vector_size]; + MOVETO(x,y,0); + *op++ = 'Z'; + + /* + * If there remain other segments (of contrasting color) to paint, + * switch pens colors and draw them + */ + if (--vector_size > 0) { + *op++ = '\033'; *op++ = '*'; *op++ = 'm'; + *op++ = mf_hp2627_pencolors[1-color]; *op++ = 'X'; + color = 1-color; + + oldx = oldy = -999; + currentformat = ASCIILABS; + *op++ = '\033'; *op++ = '*'; *op++ = 'p'; + x = *++transition_vector; + MOVETO(x,y,1); + while (vector_size-- > 0) { + x = *++transition_vector; + MOVETO(x,y,(color==init_color)); + color = 1 - color; + }; + *op++ = 'Z'; + }; + + /* + * Write the resulting plot commands, hopefully atomically + */ + (void) write(fileno(stdout), outbuf, op-outbuf); +} + +#else +int hp2627_dummy; +#endif /* HP2627WIN */ |