|
|
1.1 ! root 1: ! 2: ! 3: /* ! 4: * ! 5: * The stuff in this file used to be part of di10.c. I've taken it out of ! 6: * the main part of the post-processor because we're now accepting two ! 7: * different formats for the raster files. The original raster files had ! 8: * some rather severe limitations. They were machine dependent and used ! 9: * shorts etc. quite extensively, especially as offsets to locate glyph ! 10: * bitmaps. That put a limit on the point sizes that could be offered ! 11: * even at 240 dots per inch, but at a resolution of 300 dots an inch ! 12: * we probably wouldn't be able to access the bitmaps in a complete font ! 13: * past size 24 or so. In addition nobody's supporting the old style ! 14: * raster files or digitizing new characters for us. I've decided to ! 15: * let the new post-processor read the old style raster files along with ! 16: * the ones supplied by Imagen, although the old style won't be the ! 17: * default. ! 18: * ! 19: * ! 20: * ! 21: * The following things manage raster font information. ! 22: * The big problem is mapping desired font + size into ! 23: * available font + size. For now, a file RASTERLIST ! 24: * contains entries like ! 25: * R 6 8 10 14 999 ! 26: * I 8 10 12 999 ! 27: * ... ! 28: * This data is used to create an array "fontdata" that ! 29: * describes legal fonts and sizes, and pointers to any ! 30: * data from files that has actually been loaded. ! 31: * ! 32: */ ! 33: ! 34: ! 35: #include <stdio.h> ! 36: ! 37: #include "gen.h" /* some general purpose definitions */ ! 38: #include "ext.h" /* external variable definitions */ ! 39: #include "glyph.h" /* raster file structures */ ! 40: #include "impcodes.h" /* Impress 2.0 opcode definitions */ ! 41: #include "dimpress.h" /* we'll need a few of these defs */ ! 42: ! 43: ! 44: #define MAXFONT 60 /* max number of fonts forever */ ! 45: ! 46: ! 47: struct fontdata { ! 48: char name[4]; /* e.g., "R" or "PA" */ ! 49: int size[10]; /* e.g., 6 8 10 14 0 */ ! 50: struct fontset *fsp[10]; /* either NULL or block of data */ ! 51: }; ! 52: ! 53: ! 54: ! 55: struct Fontheader fh; ! 56: struct fontset { ! 57: int size; ! 58: int family; ! 59: struct Charparam *chp; ! 60: unsigned char *cdp; /* char data pointer */ ! 61: unsigned char *chused; /* bit-indexed; 1 if char downloaded */ ! 62: }; ! 63: ! 64: ! 65: struct fontdata fontdata[MAXFONT]; ! 66: struct fontset *fs; /* current font+size */ ! 67: int maxfonts = 0; /* number actually used */ ! 68: int nfamily = 0; /* next available family number */ ! 69: int lastfam = -1; /* last family we told Impress about */ ! 70: ! 71: extern int res; /* resolution assumed in input file */ ! 72: extern int pres; /* printer resolution */ ! 73: extern int rres; /* raster file resolution */ ! 74: extern int hpos; /* troff's position variables */ ! 75: extern int vpos; ! 76: extern float xfac; /* scaling factors */ ! 77: extern float yfac; ! 78: extern int xoffset; /* hor and vert offsets in pixels */ ! 79: extern int yoffset; ! 80: extern int font; /* using font in this position */ ! 81: extern int size; /* and want this point size */ ! 82: extern int lastfont; /* got raster files for guy last */ ! 83: extern int lastsize; /* and in this point size */ ! 84: extern int lastw; /* width of the last character */ ! 85: extern int lastx; /* Impress coordinates right now */ ! 86: extern int lasty; ! 87: extern int center; /* try and improve placement? */ ! 88: ! 89: ! 90: /*****************************************************************************/ ! 91: ! 92: ! 93: initfontdata() /* read RASTERLIST information */ ! 94: { ! 95: char name[100]; ! 96: FILE *fp; ! 97: int i, j, n; ! 98: ! 99: sprintf(name, "%s/RASTERLIST", rastdir); ! 100: if ((fp = fopen(name, "r")) == NULL) ! 101: error(FATAL, "can't open %s", name); ! 102: maxfonts = 0; ! 103: while (fscanf(fp, "%s", fontdata[maxfonts].name) != EOF) { ! 104: i = 0; ! 105: while (fscanf(fp, "%d", &n) != EOF && n < 100) { ! 106: fontdata[maxfonts].size[i] = n; ! 107: fontdata[maxfonts].fsp[i] = NULL; ! 108: i++; ! 109: } ! 110: fontdata[maxfonts].size[i] = 999; ! 111: if (++maxfonts > MAXFONT) ! 112: error(FATAL, "Too many fonts in RASTERLIST"); ! 113: } ! 114: fclose(fp); ! 115: if (debug) { ! 116: fprintf(stderr, "initfontdata(): maxfonts=%d", maxfonts); ! 117: for (i = 0; i < maxfonts; i++) { ! 118: fprintf(stderr, "%.4s ", fontdata[i].name); ! 119: for (j = 0; fontdata[i].size[j] < 100; j++) ! 120: fprintf(stderr, " %3d", fontdata[i].size[j]); ! 121: fprintf(stderr, "\n"); ! 122: } ! 123: } ! 124: } ! 125: ! 126: getfontdata(f, s) /* causes loading of font information if needed */ ! 127: char *f; ! 128: int s; ! 129: { ! 130: int fd, n, i, j; ! 131: char name[100]; ! 132: static int first = 1; ! 133: ! 134: if (first) { ! 135: initfontdata(); ! 136: first = 0; ! 137: } ! 138: ! 139: for (i = 0; i < maxfonts; i++) ! 140: if (strcmp(f, fontdata[i].name) == 0) ! 141: break; ! 142: if (i >= maxfonts) /* the requested font wasn't there */ ! 143: i = 0; /* use the first one (probably R) */ ! 144: ! 145: s = (s * pres) / rres; /* scale the requested point size */ ! 146: ! 147: /* find the best approximation to size s */ ! 148: for (j = 1; s >= fontdata[i].size[j]; j++) ! 149: ; ! 150: j--; ! 151: ! 152: /* open file if necessary */ ! 153: if (fontdata[i].fsp[j] == NULL) { ! 154: fs = (struct fontset *) malloc(sizeof(struct fontset)); ! 155: fontdata[i].fsp[j] = fs; ! 156: fs->chp = (struct Charparam *) malloc(256*sizeof(struct Charparam)); ! 157: sprintf(name, "%s/%s.%d", rastdir, f, fontdata[i].size[j]); ! 158: fd = open(name, 0); ! 159: if (fd == -1) ! 160: error(FATAL, "can't open %s", name); ! 161: read(fd, &fh, sizeof(struct Fontheader)); ! 162: read(fd, fs->chp, 256*sizeof(struct Charparam)); ! 163: fs->size = fontdata[i].size[j]; ! 164: fs->family = nfamily; ! 165: nfamily += 2; /* even-odd leaves room for big fonts */ ! 166: fs->cdp = (unsigned char *) malloc(fh.f_size); ! 167: fs->chused = (unsigned char *) malloc(256/8); ! 168: for (n = 0; n < 256/8; n++) ! 169: fs->chused[n] = 0; ! 170: n = read(fd, fs->cdp, fh.f_size); ! 171: close(fd); ! 172: } ! 173: fs = fontdata[i].fsp[j]; ! 174: } ! 175: ! 176: xychar(c, f, s, chwid, tf) ! 177: register int c; /* print this character */ ! 178: char *f; /* using this font */ ! 179: int s; /* and this point size */ ! 180: int chwid; /* use this as the char width? */ ! 181: FILE *tf; /* output written to this FILE */ ! 182: ! 183: { ! 184: register unsigned char *p; ! 185: register struct Charparam *par; ! 186: register int x, y; ! 187: char hold; ! 188: int i, n, rwid, ht, fam; ! 189: int w; ! 190: ! 191: x = hpos * xfac + 0.5; ! 192: x += xoffset; ! 193: y = vpos * yfac + 0.5; ! 194: y += yoffset; ! 195: ! 196: if (font != lastfont || size != lastsize) { ! 197: getfontdata(f, s); ! 198: lastsize = size; ! 199: lastfont = font; ! 200: } ! 201: par = fs->chp + c; ! 202: p = fs->cdp + par->c_addr; ! 203: ! 204: fam = fs->family; ! 205: if (c > 127) ! 206: fam++; ! 207: if (fam != lastfam) { ! 208: putc(ASF, tf); ! 209: putc(lastfam = fam, tf); ! 210: } ! 211: ! 212: /* first cut: ship each glyph as needed. */ ! 213: /* ignore memory use, efficiency, etc. */ ! 214: ! 215: if ( !checkbit(fs->chused, c) ) { /* 1st use of this character */ ! 216: setbit(fs->chused, c); ! 217: putc(ASGLY, tf); ! 218: putint((fam << 7) | c, tf); ! 219: par->c_width = (char)((lastw * pres) / res); ! 220: putc(par->c_width, tf); /* character width */ ! 221: hold=(char) (w = CONVINT(par->c_left) + CONVINT(par->c_right) + 1); ! 222: putc(hold,tf); ! 223: if ( center ) ! 224: putc((w - CONVINT(par->c_width)) / 2, tf); ! 225: else putc(par->c_left, tf); ! 226: /* this nonsense fixes a bug in output produced by rec.c: */ ! 227: /* when up is < 0 (and = 0?) size is one too big */ ! 228: rwid = (1 + CONVINT(par->c_left) + CONVINT(par->c_right) + BYTE-1) / BYTE; ! 229: ht = par->c_size / rwid; ! 230: par->c_down = (char)(ht - CONVINT(par->c_up)); ! 231: hold=(char)(CONVINT(par->c_down) + CONVINT(par->c_up)); ! 232: putc(hold, tf); ! 233: putc(par->c_up, tf); ! 234: for (i = par->c_size; i--; ) ! 235: putc(*p++, tf); ! 236: } ! 237: ! 238: if (y != lasty) { ! 239: putc(ASETAV, tf); ! 240: putint(y, tf); ! 241: lasty = y; ! 242: } ! 243: ! 244: if (ABS(x-lastx) > SLOP) { ! 245: putc(ASETAH, tf); ! 246: putint(x, tf); ! 247: lastx = x + (par->c_width & BMASK); ! 248: } else { ! 249: lastx += (par->c_width & BMASK); ! 250: } ! 251: ! 252: if (c <= 127) ! 253: putc(c, tf); /* fails if c > 127, probably disastrously */ ! 254: else ! 255: putc(c-128, tf); ! 256: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.