/* * This is the font specific bit of textool. * This version supports PXL format files, which are easy to use but big. */ #include "defs.h" #include #include /* for access() stuff */ #include /* for LoadAChar() */ char *index(); char *rindex(); char *sprintf(); char *strcpy(); /* procedures in sunstuff */ extern void Fatal(); extern void Warning(); /* procedures in dvistuff */ extern float ActualFactor(); extern int NoSignExtend(); extern FILE *OpenFontFile(); /* procedures here */ void FindFontFile(); void LoadAChar(); void ReadCharDefs(); /* a few global variables and data structures */ #include "globals.h" /* now to the real code */ /*-->FindFontFile*/ /**********************************************************************/ /************************ FindFontFile ******************************/ /**********************************************************************/ void FindFontFile(tfontptr, mag) struct font_entry *tfontptr; unsigned int mag; { char *direct, *tcp, *tcp1; int found; char curarea[STRSIZE]; tfontptr->font_mag = (int)((ActualFactor((int)(((float)tfontptr->s/ (float)tfontptr->d)*1000.0 + 0.5)) * #ifdef USEGLOBALMAG ActualFactor(mag) * #endif (float)RESOLUTION * 5.0) + 0.5); if (tfontptr->a != 0) { sprintf(tfontptr->name, "%s.%dpxl", tfontptr->n, tfontptr->font_mag); } else { direct = PXLpath; found = FALSE; do { tcp = index(direct, ':'); if (tcp == NULL) tcp = strlen(direct) + direct; strncpy(curarea, direct, tcp-direct); tcp1 = curarea + (tcp - direct); *tcp1++ = '/'; *tcp1++ = '\0'; sprintf(tfontptr->name, "%s%s.%dpxl", curarea, tfontptr->n, tfontptr->font_mag); found = (access(tfontptr->name, R_OK) == 0); if (*tcp) direct = tcp + 1; else direct = tcp; } while ( !found && *direct != '\0'); } } /*-->LoadAChar*/ /**********************************************************************/ /***************************** LoadAChar ****************************/ /**********************************************************************/ void LoadAChar(ptr) register struct char_entry *ptr; { register Pixrect *pr; register int nshorts, i, col, nints; register short *dp, *sp; int buffer[8]; FILE *pxlfp; pxlfp = OpenFontFile(); if (ptr->where.address.fileOffset == 0) { ptr->where.address.pixrectptr = NULL; return; } fseek(pxlfp, ptr->where.address.fileOffset, 0); if ((pr = mem_create(ptr->width, ptr->height, 1)) == NULL) { Fatal("Couldn't allocate pixrect"); return; } nshorts = (ptr->width + 15) >> 4; /* * the following test is done because * some bogus font files once caused * the pixrect to be overfilled, damaging * other font data structures */ if (nshorts != (((struct mpr_data *)pr->pr_data)->md_linebytes >> 1)) { Fatal("Pixrect too narrow for font"); return; } nints = (nshorts + 1) >> 1; dp = ((struct mpr_data *)pr->pr_data)->md_image; for (col = 0; col < ptr->height; col++) { fread(buffer, 4, nints, pxlfp); sp = (short *)&buffer[0]; for (i = nshorts; i > 0; i--) *dp++ = *sp++; } ptr->where.address.pixrectptr = pr; ptr->where.isloaded = TRUE; } /*-->ReadCharDefs*/ /**********************************************************************/ /***************************** ReadCharDefs *************************/ /**********************************************************************/ void ReadCharDefs(tfontptr, pxlfp) struct font_entry *tfontptr; FILE *pxlfp; { int t, i; register struct char_entry *tcharptr; /* temporary char_entry pointer */ if ((t = NoSignExtend(pxlfp, 4)) != PXLID) { Fatal("PXL ID = %d, can only process PXL ID = %d files", t, PXLID); return; } fseek(pxlfp, -20, 2); t = NoSignExtend(pxlfp, 4); if ((tfontptr->c != 0) && (t != 0) && (tfontptr->c != t)) Warning("font = \"%s\",\n-->font checksum = %d,\n-->dvi checksum = %d", tfontptr->name, tfontptr->c, t); (void)NoSignExtend(pxlfp, 4); /* throw away magnification */ (void)NoSignExtend(pxlfp, 4); /* throw away design size */ fseek(pxlfp, NoSignExtend(pxlfp, 4) * 4, 0); for (i = FIRSTPXLCHAR; i <= LASTPXLCHAR; i++) { tcharptr = &(tfontptr->ch[i]); tcharptr->width = NoSignExtend(pxlfp, 2); tcharptr->height = NoSignExtend(pxlfp, 2); tcharptr->xOffset= SignExtend(pxlfp, 2); tcharptr->yOffset = SignExtend(pxlfp, 2); tcharptr->where.isloaded = FALSE; tcharptr->where.address.fileOffset = NoSignExtend(pxlfp, 4) << 2; tcharptr->tfmw = ((float)NoSignExtend(pxlfp, 4)*(float)tfontptr->s) / (float)(1<<20); } if (BigPreLoad) /* load all char pixrects */ for (i = FIRSTPXLCHAR; i <= LASTPXLCHAR; i++) LoadAChar(&(tfontptr->ch[i])); }