rsalz@bbn.com (Rich Salz) (03/02/88)
Submitted-by: "Eric A. Pearce" <eap@bucsf.bu.edu> Posting-number: Volume 13, Issue 76 Archive-name: vt220fontedit This screen-oriented program lets you edit downloaded fonts for the VT220 terminal. This version runs on SysV and BSD. - Eric Pearce, Boston University #! /bin/sh # This is a shell archive. Remove anything before this line, then unpack # it by saving it into a file and typing "sh file". To overwrite existing # files, type "sh file -c". You can also feed this as standard input via # unshar, or by typing "sh <file", e.g.. If this archive is complete, you # will see the following message at the end: # "End of shell archive." # Contents: README Makefile fontedit.1 fontedit.c PATH=/bin:/usr/bin:/usr/ucb ; export PATH if test -f README -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"README\" else echo shar: Extracting \"README\" \(1482 characters\) sed "s/^X//" >README <<'END_OF_README' XWhen I first saw this posted to rn, I tried to compile this on a machine Xrunning BSD UNIX. Much to my dissapointment, It said "unable to find X/usr/include/termio.h" and thus it sat for a couple months. I was able to Xcompile it on a 3b5, but I didn't have a vt220 hooked up to it. I was doing Xsome unrelated work with ioctl calls and finally realized that it would not be Xtoo hard to convert it from System V to BSD. It also looked kind of strange Xwith the cursor on, so I turned this off. To implement this, compile with Xthe "-DCURFIX" flag in the Makefile. XI am working on a new version that uses curses and that would enable you to Xchange the file that your are working on without leaving the program. XI thought I'd post it as it is now, since it has a lot of uses right away. XImagine changing your favorite game to have objects that look like what they Xare instead of the regular characters. Also, I think people should post their Xown character sets, if they come up with some neat stuff. X Please send any comments or suggestions to: X X UUCP : ..!harvard!bu-cs!bucsb!eap X ARPANET: eap@bucsb.bu.edu X CSNET : eap%bucsb@bu-cs X X Have fun, X X - Eric Pearce X Boston University X X X X X X X X X X X X END_OF_README if test 1482 -ne `wc -c <README`; then echo shar: \"README\" unpacked with wrong size! fi # end of overwriting check fi if test -f Makefile -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"Makefile\" else echo shar: Extracting \"Makefile\" \(222 characters\) sed "s/^X//" >Makefile <<'END_OF_Makefile' X# BSD (new version, uses Berkeley specific ioctl calls) X# SYSV (old version, uses System V specific ioctl calls) X# CURFIX (turn off cursor on display) Xfontedit : fontedit.c X cc fontedit.c -O -o fontedit -DBSD -DCURFIX END_OF_Makefile if test 222 -ne `wc -c <Makefile`; then echo shar: \"Makefile\" unpacked with wrong size! fi # end of overwriting check fi if test -f fontedit.1 -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"fontedit.1\" else echo shar: Extracting \"fontedit.1\" \(1927 characters\) sed "s/^X//" >fontedit.1 <<'END_OF_fontedit.1' X.TH FONTEDIT 1 LOCAL X.SH NAME Xfontedit \- Edit fonts. X.SH SYNOPSIS X.B fontedit file X.SH DESCRIPTION X.I Fontedit Xis used to edit the down line reloadable character set (DRCS) of a VT220 Xterminal. The editor has two display areas, one for displaying the Xentry currently being manipulated, and one for displaying the complete XDRCS. Commands to the editor take the form of function keys. X.PP X.I Fontedit Xtakes one command line parameter, a file name. This file is Xused to save the character set. If the file exists when \fIfontedit\fP Xis invoked, it is read in to initialize the DRCS. The file is written Xto when \fIfontedit\fP exits. X.PP XCommands to fontedit take the form of function keys. The current Xdefinitions are: X.IP \fBHELP\fP XDisplay a help screen. X.IP \fBF6\fP XTurn the pixel under the cursor on. X.IP \fBF7\fP XTurn the pixel under the cursor off. X.IP \fBF13\fP XClear the display area. X.IP \fBFind\fP XSave the current font in the font table. Update the DRCS display. X.IP \fBSelect\fP XExtract the entry selected by the cursor in the DRCS display. X.IP \fBPrev\fP XMove the cursor to the previous entry in the DRCS display. X.IP \fBNext\fP XMove the cursor to the next entry in the DRCS display. X.IP \fBInsert\fP XInsert a blank line at the current cursor position. The bottom row is lost. X.IP \fBRemove\fP XRemove the row at the current cursor position. All rows below the Xcurrent one are shifted up. X.IP \fBCursors\fP XMove the cursor in the main display area. X.PP XIf the screen gets garbled, press <control-L>. X.PP XTo exit \fIfontedit\fP, press <control-D>. The DRCS will be saved in X\fIfile\fP. To exit without saving the DRCS, hit interrupt (usually XDEL). X.SH DIAGNOSTICS X.I Fontedit Xwill issue a warning when the entry being worked on is not saved, and Xsome potentially destructive command, like \fBSelect\fP is used. To Xoverride the warning message, immediately reissue the command. X.SH AUTHOR XGreg Franks. X X END_OF_fontedit.1 if test 1927 -ne `wc -c <fontedit.1`; then echo shar: \"fontedit.1\" unpacked with wrong size! fi # end of overwriting check fi if test -f fontedit.c -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"fontedit.c\" else echo shar: Extracting \"fontedit.c\" \(17714 characters\) sed "s/^X//" >fontedit.c <<'END_OF_fontedit.c' X/* X * fontedit X * Fonteditor for VT220 X * X * BUGS: X * o Cursor motion is less than optimal (but who cares at 9600), X * X * COMPILE: X * cc -O fontedit.c -o fontedit X * (use Makefile) X * X * Copyright (c) 1987 by Greg Franks. X * X * Permission is granted to do anything you want with this program X * except claim that you wrote it. X * X * X * REVISION HISTORY: X * X * Nov 21, 1987 - Fixed man page to say "Fontedit" instead of "Top" X * Nov 22, 1987 - Added BSD Compatible ioctl, turned cursor on/off X * - eap@bucsf.bu.edu X */ X X#include <stdio.h> X#ifdef SYSV X#include <sys/termio.h> X#endif SYSV X#ifdef BSD X#include <sys/ioctl.h> X#endif BSD X#include <signal.h> X X#ifdef CURFIX X#define CURSORON "\033[?25h" X#define CURSOROFF "\033[?25l" X#endif CURFIX X X#define MAX_ROWS 10 X#define MAX_COLS 8 X Xtypedef enum { false, true } bool; X X#define KEY_FIND 0x0100 X#define KEY_INSERT 0x0101 X#define KEY_REMOVE 0x0102 X#define KEY_SELECT 0x0103 X#define KEY_PREV 0x0104 X#define KEY_NEXT 0x0105 X#define KEY_F6 0X0106 X#define KEY_F7 0x0107 X#define KEY_F8 0x0108 X#define KEY_F9 0x0109 X#define KEY_F10 0x010a X#define KEY_F11 0x010b X#define KEY_F12 0x010c X#define KEY_F13 0x010d X#define KEY_F14 0x010e X#define KEY_HELP 0x010f X#define KEY_DO 0x0110 X#define KEY_F17 0x0111 X#define KEY_F18 0x0112 X#define KEY_F19 0x0113 X#define KEY_F20 0x0114 X#define KEY_UP 0x0115 X#define KEY_DOWN 0x0116 X#define KEY_RIGHT 0x0117 X#define KEY_LEFT 0x0118 X X/* X * Position of main drawing screen. X */ X X#define ROW_OFFSET 3 X#define COL_OFFSET 10 X X/* X * Position of the DRCS table. X */ X X#define TABLE_ROW 4 X#define TABLE_COL 50 X X/* X * X */ X X#define ERROR_ROW 20 X#define ERROR_COL 40 X Xbool display_table[MAX_ROWS][MAX_COLS]; X X#define TOTAL_ENTRIES (128 - 32) X#define SIXELS_PER_CHAR 16 X Xchar font_table[TOTAL_ENTRIES][SIXELS_PER_CHAR]; Xunsigned int current_entry; X X#ifdef SYSV Xstruct termio old_stty, new_stty; X#endif SYSV X#ifdef BSD Xstruct sgttyb old_stty, new_stty; X#endif BSD X XFILE * font_file = (FILE *)0; X X X/* X * Interrupt X * Exit gracefully. X */ X Xinterrupt() X{ X void clear_screen(); X#ifdef CURFIX X printf("%s\n",CURSORON); X#endif CURFIX X#ifdef SYSV X ioctl( 0, TCSETA, &old_stty ); X#endif SYSV X#ifdef BSD X ioctl( 0, TIOCSETP, &old_stty ); X#endif BSD X clear_screen(); X exit( 0 ); X} X X X/* X * Main X * Grab input/output file and call main command processor. X */ X Xmain( argc, argv ) Xint argc; Xchar *argv[]; X{ X void command(), init_restore(), clear_screen(); X void save_table(), get_table(), extract_entry(); X X if ( argc != 2 ) { X fprintf( stderr, "useage: fontedit filename\n" ); X exit( 1 ); X } X X printf( "Press HELP for help\n" ); X printf( "\033P1;1;2{ @\033\\" ); /* Clear font buffer */ X fflush( stdout ); X sleep( 1 ); /* Let terminal catch up */ X /* otherwise we get frogs */ X X if ( ( font_file = fopen( argv[1], "r" ) ) != (FILE *)0 ) { X get_table( font_file ); X fclose( font_file ); X } X X if ( ( font_file = fopen( argv[1], "r+" ) ) == (FILE *)0 ) { X fprintf( stderr, "Cannot open %s for writing\n", argv[1] ); X exit( 1 ); X } X#ifdef CURFIX X printf("%s\n",CURSOROFF); X#endif CURFIX X#ifdef SYSV X ioctl( 0, TCGETA, &old_stty ); X#endif SYSV X#ifdef BSD X ioctl( 0, TIOCGETP, &old_stty ); X#endif BSD X signal( SIGINT, interrupt ); X X new_stty = old_stty; X#ifdef SYSV X new_stty.c_lflag &= ~ICANON; X new_stty.c_cc[VMIN] = 1; X ioctl( 0, TCSETA, &new_stty ); X#endif SYSV X#ifdef BSD X new_stty.sg_flags |= CBREAK; X new_stty.sg_flags &= ~ECHO; X ioctl( 0, TIOCSETP, &new_stty ); X#endif BSD X current_entry = 1; X extract_entry( current_entry ); X init_restore(); X command(); X#ifdef SYSV X ioctl( 0, TCSETA, &old_stty ); X#endif SYSV X#ifdef BSD X ioctl( 0, TIOCSETP, &old_stty ); X#endif BSD X clear_screen(); X X /* Overwrite the old file. */ X X fseek( font_file, 0L, 0 ); X save_table( font_file ); X fclose( font_file ); X#ifdef CURFIX X printf("%s\n",CURSORON); X#endif CURFIX X} X X X X/* X * Command X * Process a function key. X * X * The user cannot fill in slots 0 or 95 (space and del respecitively). X */ X Xvoid Xcommand() X{ X register int c; X register int row, col; X register int i, j; X bool change, error, override; X X void build_entry(), extract_entry(), send_entry(), print_entry(); X void highlight(), draw_current(), init_restore(), help(); X void warning(); X X change = false; X error = false; X override = false; X row = 0; col = 0; X highlight( row, col, true ); X X for ( ;; ) { X c = get_key(); X highlight( row, col, false ); /* turn cursor off */ X X if ( error ) { X move ( ERROR_ROW, ERROR_COL ); X printf( "\033[K" ); /* Clear error message */ X move ( ERROR_ROW+1, ERROR_COL ); X printf( "\033[K" ); /* Clear error message */ X error = false; X } else { X override = false; X } X X switch ( c ) { X X case KEY_FIND: /* update DRCS */ X if ( !change && !override ) { X warning( "No changes to save" ); X override = true; X error = true; X } else { X build_entry( current_entry ); X send_entry( current_entry ); X print_entry( current_entry, true ); X change = false; X } X break; X X case KEY_F6: /* Turn on pixel */ X change = true; X display_table[row][col] = true; X highlight( row, col, false ); X col = ( col + 1 ) % MAX_COLS; X if ( col == 0 ) X row = ( row + 1 ) % MAX_ROWS; X break; X X case KEY_F7: /* Turn off pixel */ X change = true; X display_table[row][col] = false; X highlight( row, col, false ); X col = ( col + 1 ) % MAX_COLS; X if ( col == 0 ) X row = ( row + 1 ) % MAX_ROWS; X break; X X case KEY_INSERT: /* Insert a blank row */ X change = true; X for ( j = 0; j < MAX_COLS; ++j ) { X for ( i = MAX_ROWS - 1; i > row; --i ) { X display_table[i][j] = display_table[i-1][j]; X } X display_table[row][j] = false; X } X draw_current(); X break; X X case KEY_REMOVE: /* Remove a row */ X change = true; X for ( j = 0; j < MAX_COLS; ++j ) { X for ( i = row; i < MAX_ROWS - 1; ++i ) { X display_table[i][j] = display_table[i+1][j]; X } X display_table[MAX_ROWS-1][j] = false; X } X draw_current(); X break; X X case KEY_F13: /* Clear buffer */ X if ( change && !override ) { X warning( "Changes not saved" ); X error = true; X override = true; X } else { X for ( j = 0; j < MAX_COLS; ++j ) { X for ( i = 0; i < MAX_ROWS; ++i ) { X display_table[i][j] = false; X } X } X draw_current(); X } X break; X X case KEY_SELECT: /* Select font from DRCS */ X if ( change && !override ) { X warning( "Changes not saved" ); X error = true; X override = true; X } else { X extract_entry( current_entry ); X draw_current(); X } X break; X X case KEY_PREV: /* Move to prev entry in DRCS */ X if ( change && !override ) { X warning( "Changes not saved" ); X override = true; X error = true; X } else { X print_entry( current_entry, false ); X current_entry = current_entry - 1; X if ( current_entry == 0 ) X current_entry = TOTAL_ENTRIES - 2; X print_entry( current_entry, true ); X } X break; X X case KEY_NEXT: /* Move to next entry in DRCS */ X if ( change && !override ) { X warning( "Changes not saved" ); X override = true; X error = true; X } else { X print_entry( current_entry, false ); X current_entry = current_entry + 1; X if ( current_entry == TOTAL_ENTRIES - 1 ) X current_entry = 1; X print_entry( current_entry, true ); X } X break; X X case KEY_UP: /* UP one row. */ X if ( row == 0 ) X row = MAX_ROWS; X row = row - 1; X break; X X case KEY_DOWN: /* Guess. */ X row = ( row + 1 ) % MAX_ROWS; X break; X X case KEY_RIGHT: X col = ( col + 1 ) % MAX_COLS; X break; X X case KEY_LEFT: X if ( col == 0 ) X col = MAX_COLS; X col = col - 1; X break; X X case KEY_HELP: /* Display helpful info */ X clear_screen(); X help(); X c = getchar(); X init_restore(); X break; X X case '\004': /* All done! */ X return; X X case '\f': /* Redraw display */ X init_restore(); X break; X X default: /* user is a klutzy typist */ X move ( ERROR_ROW, ERROR_COL ); X printf( "Unknown key: " ); X if ( c < 0x20 ) { X printf( "^%c", c ); X } else if ( c < 0x0100 ) { X printf( "%c", c ); X } else { X printf( "0x%04x", c ); X } X fflush( stdout ); X error = true; X } X X highlight( row, col, true ); /* turn cursor on */ X } X} X X X Xchar *key_table[] = { X "\033[1~", /* Find */ X "\033[2~", /* Insert */ X "\033[3~", /* Remove */ X "\033[4~", /* Select */ X "\033[5~", /* Prev */ X "\033[6~", /* Next */ X "\033[17~", X "\033[18~", X "\033[19~", X "\033[20~", X "\033[21~", X "\033[23~", X "\033[24~", X "\033[25~", X "\033[26~", X "\033[28~", X "\033[29~", X "\033[31~", X "\033[32~", X "\033[33~", X "\033[34~", X "\033[A", X "\033[B", X "\033[C", X "\033[D", X (char *)0 }; X X/* X * get_key X * Convert VT220 escape sequence into something more reasonable. X */ X Xint Xget_key() X{ X register char *p; X char s[10]; X register int i, j; X X p = s; X for ( i = 0; i < 10; ++i ) { X *p = getchar(); X if ( i == 0 && *p != '\033' ) X return( (int)*p ); /* Not an escape sequence */ X if ( *p != '\033' && *p < 0x0020 ) X return( (int)*p ); /* Control character */ X *++p = '\0'; /* Null terminate */ X for ( j = 0; key_table[j]; ++j ) { X if ( strcmp( s, key_table[j] ) == 0 ) X return( j | 0x0100 ); X } X } X return( -1 ); X} X X X X/* X * pad X * Emit nulls so that the terminal can catch up. X */ X Xpad() X{ X int i; X X for ( i = 0; i < 20; ++i ) X putchar( '\000' ); X fflush( stdout ); X} X X X X/* X * init_restore X * refresh the main display table. X */ X Xvoid Xinit_restore() X{ X register int row, col; X register int i; X X void draw_current(), clear_screen(), print_entry(); X X clear_screen(); X X for ( col = 0; col < MAX_COLS; ++col ) { X move( ROW_OFFSET - 2, col * 3 + COL_OFFSET + 1 ); X printf( "%d", col ); X } X move( ROW_OFFSET - 1, COL_OFFSET ); X printf( "+--+--+--+--+--+--+--+--+" ); X move( ROW_OFFSET + MAX_ROWS * 2, COL_OFFSET ); X printf( "+--+--+--+--+--+--+--+--+" ); X X for ( row = 0; row < MAX_ROWS; ++row ) { X if ( row != 0 && row != 7 ) { X move( row * 2 + ROW_OFFSET, COL_OFFSET - 2 ); X printf( "%d|", row ); X move( row * 2 + ROW_OFFSET + 1, COL_OFFSET - 1 ); X printf( "|" ); X move( row * 2 + ROW_OFFSET, COL_OFFSET + MAX_COLS * 3 ); X printf( "|" ); X move( row * 2 + ROW_OFFSET + 1, COL_OFFSET + MAX_COLS * 3 ); X printf( "|" ); X } else { X move( row * 2 + ROW_OFFSET, COL_OFFSET - 2 ); X printf( "%d*", row ); X move( row * 2 + ROW_OFFSET + 1, COL_OFFSET - 1 ); X printf( "*" ); X move( row * 2 + ROW_OFFSET, COL_OFFSET + MAX_COLS * 3 ); X printf( "*" ); X move( row * 2 + ROW_OFFSET + 1, COL_OFFSET + MAX_COLS * 3 ); X printf( "*" ); X } X } X draw_current(); X X move( TABLE_ROW - 1, TABLE_COL - 1 ); X printf( "+-+-+-+-+-+-+-+-+-+-+-+-+" ); X move( TABLE_ROW + 8 * 2 - 1, TABLE_COL - 1 ); X printf( "+-+-+-+-+-+-+-+-+-+-+-+-+" ); X for ( i = 0; i < 8; ++i ) { X move ( TABLE_ROW + i * 2, TABLE_COL - 1 ); X printf( "|" ); X move ( TABLE_ROW + i * 2 + 1, TABLE_COL - 1 ); X printf( "+" ); X move ( TABLE_ROW + i * 2, TABLE_COL + 12 * 2 - 1); X printf( "|" ); X move ( TABLE_ROW + i * 2 + 1, TABLE_COL +12 * 2 - 1); X printf( "+" ); X } X for ( i = 0; i < TOTAL_ENTRIES; ++i ) X print_entry( i, (i == current_entry) ? true : false ); X} X X X X/* X * draw_current X * Draw the complete current entry. X */ X Xvoid Xdraw_current() X{ X register int row, col; X X printf( "\033)0" ); /* Special graphics in G1 */ X printf( "\016" ); /* Lock in G1 (SO) */ X X for ( row = 0; row < MAX_ROWS; ++row ) { X for ( col = 0; col < MAX_COLS; ++col ) { X if ( display_table[row][col] ) { X move( row * 2 + ROW_OFFSET, col * 3 + COL_OFFSET ); X printf( "\141\141\141" ); X move( row * 2 + ROW_OFFSET + 1, col * 3 + COL_OFFSET ); X printf( "\141\141\141" ); X } else { X move( row * 2 + ROW_OFFSET, col * 3 + COL_OFFSET ); X printf( " " ); /* erase splat */ X move( row * 2 + ROW_OFFSET + 1, col * 3 + COL_OFFSET ); X printf( " " ); /* erase splat */ X } X } X pad(); X } X printf( "\017" ); /* Lock in G0 (SI) */ X fflush( stdout ); X} X X X X/* X * highlight X * Draw the cursor in the main display area. X */ X Xvoid Xhighlight( row, col, on ) Xunsigned int row, col; Xbool on; X{ X X printf( "\033)0" ); /* Special graphics in G1 */ X printf( "\016" ); /* Lock in G1 (SO) */ X if ( on ) { X printf( "\033[7m" ); /* Reverse video cursor */ X } X X if ( display_table[row][col] ) { X move( row * 2 + ROW_OFFSET, col * 3 + COL_OFFSET ); X printf( "\141\141\141" ); X move( row * 2 + ROW_OFFSET + 1, col * 3 + COL_OFFSET ); X printf( "\141\141\141" ); X } else { X move( row * 2 + ROW_OFFSET, col * 3 + COL_OFFSET ); X printf( " " ); /* erase splat */ X move( row * 2 + ROW_OFFSET + 1, col * 3 + COL_OFFSET ); X printf( " " ); /* erase splat */ X } X pad(); X printf( "\017" ); /* Lock in G0 (SI) */ X printf( "\033[0m" ); /* normal video */ X printf( "\b" ); /* Back up one spot */ X fflush( stdout ); X} X X X X/* X * Clear_screen X */ X Xvoid Xclear_screen() X{ X printf( "\033[H\033[J" ); /* Clear screen. */ X fflush( stdout ); X} X X X X/* X * move X */ X Xmove( y, x ) Xint y, x; X{ X printf( "\033[%d;%df", y, x ); X} X X X X/* X * Build_entry X * Convert the bit pattern used in the main display area into something X * that the vt220 can digest - namely sixels... X */ X Xvoid Xbuild_entry( entry_no ) Xunsigned int entry_no; X{ X register int row, col; X register unsigned int mask; X X for ( col = 0; col < 8; ++col ) { X X /* Top set of sixels */ X X mask = 0; X for ( row = 5; row >= 0; --row ) { X mask = mask << 1; X if ( display_table[row][col] ) X mask |= 1; X } X font_table[entry_no][col] = mask + 077; X X /* Bottom set of sixels */ X X mask = 0; X for ( row = 9; row >= 6; --row ) { X mask = mask << 1; X if ( display_table[row][col] ) X mask |= 1; X } X font_table[entry_no][col+8] = mask + 077; X } X X} X X X X/* X * Extract_engry X * convert sixel representation into an array of bits. X */ X Xvoid Xextract_entry( entry_no ) Xunsigned int entry_no; X{ X register int row, col; X register unsigned int mask; X X for ( col = 0; col < 8; ++col ) { X X /* Top set of sixels */ X X mask = font_table[entry_no][col]; X if ( mask >= 077 ) X mask -= 077; X else X mask = 0; /* Bogus entry */ X X for ( row = 0; row <= 5; ++row ) { X display_table[row][col] = (bool)(mask & 0x0001); X mask = mask >> 1; X } X X /* Bottom set of sixels */ X X mask = font_table[entry_no][col+8]; X if ( mask >= 077 ) X mask -= 077; X else X mask = 0; X X for ( row = 6; row <= 9; ++row ) { X display_table[row][col] = (bool)(mask & 0x0001); X mask = mask >> 1; X } X } X X} X X X X/* X * Send_entry X * Emit the stuff used by the VT220 to load a character into the X * DRCS. We could, of course, send more than one entry at a time... X */ X Xvoid Xsend_entry( entry_no ) Xint entry_no; X{ X register char *fp = font_table[entry_no]; X X printf( "\033P1;%d;1;0;0;0{ @%c%c%c%c%c%c%c%c/%c%c%c%c%c%c%c%c\033\\", X entry_no, X fp[ 0], fp[ 1], fp[ 2], fp[ 3], fp[ 4], fp[ 5], fp[ 6], fp[ 7], X fp[ 8], fp[ 9], fp[10], fp[11], fp[12], fp[13], fp[14], fp[15] ); X} X X X X/* X * Print_entry X * The terminal normally has G0 in GL. We don't want to change X * this, nor do we want to use GR. Sooooo send out the necessary X * magic for shifting in G2 temporarily for the character that we X * want to display. X */ X Xvoid Xprint_entry( entry_no, highlight ) Xregister unsigned int entry_no; Xbool highlight; X{ X X register int y, x; X X y = entry_no & 0x07; X x = entry_no >> 3 & 0x1f; X entry_no += 32; /* Map up to G set */ X X move( y * 2 + TABLE_ROW, x * 2 + TABLE_COL ); X X if ( highlight ) X printf( "\033[7m" ); X X printf( "\033* @" ); /* select DRCS into G2 */ X printf( "\033N" ); /* select single shift */ X printf( "%c", entry_no ); /* Draw the character */ X X if ( highlight ) X printf( "\033[0m" ); X} X X X X/* X * Save_table X * Save a font table X */ X Xvoid Xsave_table( font_file ) XFILE *font_file; X{ X register char *fp; X register int i; X X for ( i = 0; i < TOTAL_ENTRIES; ++i ) { X fp = font_table[i]; X fprintf( font_file, "\033P1;%d;1;0;0;0{ @%c%c%c%c%c%c%c%c/%c%c%c%c%c%c%c%c\033\\\n", X i, X fp[ 0], fp[ 1], fp[ 2], fp[ 3], fp[ 4], fp[ 5], fp[ 6], fp[ 7], X fp[ 8], fp[ 9], fp[10], fp[11], fp[12], fp[13], fp[14], fp[15] ); X } X} X X X X/* X * Get_table X * Extract font table entries from a file X */ X Xvoid Xget_table( font_file ) XFILE *font_file; X{ X char s[256]; X register char *p; X char *fp; X int i; X register int j; X X while( fgets( s, 255, font_file ) ) { X if ( strncmp( s, "\033P1;", 4 ) != 0 ) X continue; /* Bogus line */ X p = &s[4]; X if ( sscanf( p, "%d", &i ) != 1 ) X continue; /* Illegal entry number */ X X if ( i <= 0 || TOTAL_ENTRIES <= i ) X continue; /* Bogues entry */ X X fp = font_table[i]; X X while ( *p && *p != '@' ) X ++p; /* Skip to font definition */ X if ( ! *p++ ) X continue; /* Skip @ */ X X for ( j = 0; *p && *p != '\033' && j < 16; ++j, ++p ) { X if ( *p == '/' ) { X j = 8; X ++p; X } X fp[j] = *p; X } X send_entry( i ); X } X} X X X X/* X * Help X * Print out help information. X */ X Xvoid Xhelp() X{ X printf( "Font editor\n\n" ); X printf( "F6 - Pixel on\n" ); X printf( "F7 - Pixel off\n" ); X printf( "F13 - Clear display area\n" ); X printf( "HELP - This screen\n" ); X printf( "FIND - Update font table\n" ); X printf( "INSERT - Insert a blank row\n" ); X printf( "REMOVE - Remove a row\n" ); X printf( "SELECT - Select current font table entry\n" ); X printf( "PREV - Move to previous font table entry\n" ); X printf( "NEXT - Move to next font table entry\n" ); X printf( "^D - Exit\n" ); X printf( "\n\n\n\nPress any key to continue\n" ); X} X X X X/* X * Warning X * Issue a warning to the regarding the current status. X */ X Xvoid Xwarning( s ) Xchar *s; X{ X move( ERROR_ROW, ERROR_COL ); X printf( "Warning: %s!\n", s ); X move( ERROR_ROW+1, ERROR_COL ); X printf( " Reissue command to override\n" ); X} END_OF_fontedit.c if test 17714 -ne `wc -c <fontedit.c`; then echo shar: \"fontedit.c\" unpacked with wrong size! fi # end of overwriting check fi echo shar: End of shell archive. exit 0 -- For comp.sources.unix stuff, mail to rsalz@uunet.uu.net.