Annotation of researchv9/X11/src/X.V11R1/server/dix/fonts.c, revision 1.1.1.1

1.1       root        1: /************************************************************************
                      2: Copyright 1987 by Digital Equipment Corporation, Maynard, Massachusetts,
                      3: and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
                      4: 
                      5:                         All Rights Reserved
                      6: 
                      7: Permission to use, copy, modify, and distribute this software and its 
                      8: documentation for any purpose and without fee is hereby granted, 
                      9: provided that the above copyright notice appear in all copies and that
                     10: both that copyright notice and this permission notice appear in 
                     11: supporting documentation, and that the names of Digital or MIT not be
                     12: used in advertising or publicity pertaining to distribution of the
                     13: software without specific, written prior permission.  
                     14: 
                     15: DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
                     16: ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
                     17: DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
                     18: ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
                     19: WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
                     20: ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
                     21: SOFTWARE.
                     22: 
                     23: ************************************************************************/
                     24: 
                     25: /* $Header: fonts.c,v 1.46 87/09/09 13:23:03 rws Exp $ */
                     26: 
                     27: #define NEED_REPLIES
                     28: #include "X.h"
                     29: #include "Xmd.h"
                     30: #include "Xproto.h"
                     31: #include "dixfontstr.h"
                     32: #include "fontstruct.h"
                     33: #include "scrnintstr.h"
                     34: #include "resource.h"
                     35: #include "osstruct.h"
                     36: #include "dix.h"
                     37: #include "cursorstr.h"
                     38: #include "misc.h"
                     39: #include "opaque.h"
                     40: 
                     41: static FontPtr         pFontHead = NullFont;
                     42: extern FontPtr         defaultFont;
                     43: 
                     44: 
                     45: /*
                     46:  * adding RT_FONT prevents conflict with default cursor font
                     47:  */
                     48: SetDefaultFont( defaultfontname)
                     49:     char *     defaultfontname;
                     50: {
                     51:     FontPtr    pf;
                     52: 
                     53:     if ((pf =OpenFont( strlen( defaultfontname), defaultfontname)) == NullFont)
                     54:        return FALSE;
                     55: 
                     56:     AddResource( FakeClientID(0), RT_FONT, pf, CloseFont, RC_CORE);
                     57:     defaultFont = pf;
                     58:     return TRUE;
                     59: }
                     60: 
                     61: /*
                     62:  * Check reference count first, load font only if necessary.
                     63:  */
                     64: FontPtr 
                     65: OpenFont( lenfname, pfilename)
                     66:     int                lenfname;
                     67:     char *     pfilename;
                     68: {
                     69:     FontPtr    pfont;
                     70:     int                lenpname;
                     71:     char *     ppathname;
                     72:     FID                pf;
                     73:     int                nscr;
                     74:     ScreenPtr  pscr;
                     75: 
                     76:     FontPtr    ReadNFont();
                     77: 
                     78:     /*
                     79:      * call os-dependent code
                     80:      */
                     81:     if ( (lenpname = ExpandFontName( &ppathname, lenfname, pfilename)) == 0)
                     82:     {
                     83: #ifdef notdef
                     84:        ErrorF( "OpenFont: ExpandFontName failed to find file '%s', (len = %d)\n",
                     85:                pfilename, lenfname);
                     86: #endif
                     87:        return NullFont;
                     88:     }
                     89:     /*
                     90:      * first look up font name in list of opened fonts 
                     91:      */
                     92:     for (   pfont = pFontHead;
                     93:            pfont != NullFont;
                     94:            pfont = pfont->next)
                     95:        if ( lenpname == pfont->lenpname
                     96:          && strncmp( pfont->pathname, ppathname, pfont->lenpname) == 0)
                     97:        {
                     98:            /*
                     99:             * found it!
                    100:             */
                    101:            pfont->refcnt += 1;
                    102:            Xfree(ppathname);
                    103:            return pfont;
                    104:        }
                    105:        
                    106:     /*
                    107:      * if not found in fonts list, read it off disk
                    108:      */
                    109: 
                    110:     if ( (pf = FiOpenForRead( lenpname, ppathname)) == NullFID)
                    111:     {
                    112: #ifdef notdef
                    113:        ErrorF( 
                    114:                "OpenFont: failed to open font file %s\n",
                    115:                ppathname);
                    116: #endif
                    117:        Xfree(ppathname);
                    118:        return NullFont;
                    119:     }
                    120:     pfont = ReadNFont( pf);
                    121:     FiClose( pf);
                    122: 
                    123:     if ( pfont == NullFont)
                    124:     {
                    125: #ifdef notdef
                    126:        ErrorF(  "OpenFont: ReadNFont failed on file %s\n", ppathname);
                    127: #endif
                    128:        Xfree(ppathname);
                    129:        return NullFont;
                    130:     }
                    131: 
                    132:     pfont->lenpname = lenpname;
                    133:     pfont->pathname = (char *)Xalloc( lenpname);       /* record pathname */
                    134:     strncpy( pfont->pathname, ppathname, lenpname);
                    135: 
                    136:     pfont->refcnt = 1;
                    137:     pfont->next = pFontHead;                   /* prepend to fonts list */
                    138:     pFontHead = pfont;
                    139: 
                    140:     /*
                    141:      * since this font has been newly read off disk, ask each screen to
                    142:      * realize it.
                    143:      */
                    144:     for ( nscr=0, pscr=screenInfo.screen;
                    145:          nscr<screenInfo.numScreens;
                    146:          nscr++, pscr++)
                    147:     {
                    148:         if ( pscr->RealizeFont)
                    149:            ( *pscr->RealizeFont)( pscr, pfont);
                    150:     }
                    151:     Xfree(ppathname);
                    152:     return pfont;
                    153: }
                    154: 
                    155: /*
                    156:  * Decrement font's ref count, and free storage if ref count equals zero
                    157:  */
                    158: void
                    159: CloseFont( pfont)
                    160:     FontPtr    pfont;
                    161: {
                    162:     FontPtr    ptf;
                    163:     FontPtr    pbtf = NullFont;
                    164:     int                nscr;
                    165:     ScreenPtr  pscr;
                    166: 
                    167:     if (pfont == NullFont)
                    168:         return ;
                    169:     for (   ptf = pFontHead;
                    170:            ptf != NullFont;
                    171:            ptf = ptf->next)
                    172:     {
                    173:        if ( ptf == pfont || ptf == NullFont)
                    174:            break;
                    175:        pbtf = ptf;
                    176:     }
                    177:     if ( ptf == NullFont)
                    178:     {
                    179:        ErrorF(  "CloseFont: couldn't find font to be closed %x\n", ptf);
                    180:        return;
                    181:     }
                    182:     if ( --ptf->refcnt == 0)
                    183:     {
                    184:        if ( pbtf == NullFont)          /* unlink ptf */
                    185:            pFontHead = ptf->next;
                    186:        else
                    187:            pbtf->next = ptf->next;
                    188: 
                    189:        /*
                    190:         * since the last reference is gone, ask each screen to
                    191:         * free any storage it may have allocated locally for it.
                    192:         */
                    193:        for ( nscr=0, pscr=screenInfo.screen;
                    194:              nscr<screenInfo.numScreens;
                    195:              nscr++, pscr++)
                    196:        {
                    197:            if ( pscr->UnrealizeFont)
                    198:                ( *pscr->UnrealizeFont)( pscr, ptf);
                    199:        }
                    200:        Xfree( ptf->pathname);
                    201:        Xfree( ptf);
                    202:        if (pfont == defaultFont)
                    203:            defaultFont = NULL;
                    204:     }
                    205: }
                    206: 
                    207: 
                    208: /*
                    209:  * description
                    210:  *
                    211:  * Allocates storage with Xalloc(), and returns a pointer to it.
                    212:  * Client can call Xfree() to deallocate font.
                    213:  *
                    214:  * file I/O is all in this routine
                    215:  */
                    216: FontPtr 
                    217: ReadNFont( fp)
                    218:     FID                fp;     /* caller has to FiOpenForRead the file himself */
                    219: {
                    220:     FontPtr    pfont;
                    221:     FontInfoRec        fi;
                    222:     DIXFontProp *pdfp;
                    223:     FontPropPtr        pffp;
                    224:     char       *propspace;
                    225:     int                bytestoread, bytestoalloc;
                    226:     int                bytesdata;
                    227:     int                i;
                    228:     char *strings;
                    229:        
                    230:     /* swap bytes? XXX */
                    231: 
                    232:     bytestoread = BYTESOFFONTINFO(&fi);
                    233:     if ( FiRead( &fi, 1, bytestoread, fp) != bytestoread)
                    234:     {
                    235:        ErrorF("ReadNFont: unexpected EOF\n");
                    236:         return NullFont;
                    237:     }
                    238: 
                    239:     if (fi.version1 != FONT_FILE_VERSION || fi.version2 != FONT_FILE_VERSION)
                    240:     {
                    241:        ErrorF("ReadNFont: bad font version; expected %d, got %d and %d\n",
                    242:                FONT_FILE_VERSION, fi.version1, fi.version2);
                    243:        return NullFont;
                    244:     }
                    245: 
                    246:     bytesdata = BYTESOFFONTINFO(&fi);
                    247:     bytesdata += BYTESOFCHARINFO(&fi);
                    248:     bytesdata += BYTESOFGLYPHINFO(&fi);
                    249: 
                    250:     bytestoalloc = BYTESOFFONTINFO(&fi)+bytesdata+BYTESOFPROPINFO(&fi);
                    251:     pfont = (FontPtr ) Xalloc(bytestoalloc);
                    252: 
                    253:     bytestoread = bytesdata - BYTESOFFONTINFO(&fi);
                    254:     if ( FiRead((char *)(&pfont[1]) + BYTESOFFONTINFO(&fi),
                    255:                1, bytestoread,
                    256:                fp ) != bytestoread)
                    257:     {
                    258:        ErrorF("ReadNFont: unexpected EOF\n");
                    259:        Xfree(pfont);
                    260:         return NullFont;
                    261:     }
                    262: 
                    263:     /*
                    264:      * now fix up pointers
                    265:      */
                    266:     pfont->pFI = (FontInfoPtr)&pfont[1];
                    267:     *pfont->pFI = fi;  /* copy date previously read */
                    268:     
                    269:     pfont->pCI = ADDRCharInfoRec(pfont->pFI);
                    270: 
                    271:     pfont->pGlyphs = ADDRCHARGLYPHS(pfont->pFI);
                    272: 
                    273:     pfont->pFP = ADDRXFONTPROPS(pfont->pFI);
                    274: 
                    275:     /* now read and atom'ize properties */
                    276: 
                    277:     bytestoalloc = BYTESOFPROPINFO(pfont->pFI) + BYTESOFSTRINGINFO(pfont->pFI);
                    278:     propspace = (char *) Xalloc(bytestoalloc);
                    279:     
                    280:     pffp = (FontPropPtr)propspace;
                    281:     strings = propspace + BYTESOFPROPINFO(pfont->pFI);
                    282:     
                    283:     bytestoread = bytestoalloc;
                    284:     if ( FiRead(
                    285:                pffp, 1,
                    286:                bytestoread,
                    287:                fp) != bytestoread)
                    288:     {
                    289:        ErrorF("ReadNFont: unexpected EOF\n");
                    290:        Xfree(pfont);
                    291:        Xfree(propspace);
                    292:         return NullFont;
                    293:     }
                    294: 
                    295:     for (i=0, pdfp=pfont->pFP; i<fi.nProps; i++, pdfp++, pffp++)
                    296:     {
                    297:        pdfp->name = MakeAtom(
                    298:                &strings[pffp->name], strlen(&strings[pffp->name]), 1);
                    299:        if (pffp->indirect)
                    300:                pdfp->value = (INT32)MakeAtom(
                    301:                    &strings[pffp->value], strlen(&strings[pffp->value]), 1);
                    302:        else
                    303:                pdfp->value = pffp->value;
                    304:     }
                    305: 
                    306:     Xfree(propspace);
                    307: 
                    308:     return pfont;
                    309: }
                    310: 
                    311: Bool
                    312: DescribeFont(pfontname, lenfname, pfi, ppfp)
                    313:     char *pfontname;
                    314:     int lenfname;
                    315:     FontInfoPtr pfi;
                    316:     DIXFontPropPtr *ppfp;      /* return */
                    317: {
                    318:     FontPtr pfont;
                    319:     FID pf;
                    320:     int i;
                    321:     char *ppathname;
                    322:     int lenpname;
                    323:     int bytesskip, bytesprops;
                    324:     DIXFontPropPtr pdfp;
                    325:     FontPropPtr pffp, temp;
                    326:     char *strings;
                    327: 
                    328:     if ((lenpname = ExpandFontName(&ppathname, lenfname, pfontname)) == 0)
                    329:         return(FALSE);
                    330:     /*
                    331:      * first look up font name in list of opened fonts 
                    332:      */
                    333:     for (   pfont = pFontHead;
                    334:            pfont != NullFont;
                    335:            pfont = pfont->next)
                    336:        if ( lenpname == pfont->lenpname
                    337:          && strncmp( pfont->pathname, ppathname, pfont->lenpname) == 0)
                    338:        {
                    339:            *pfi = *pfont->pFI;
                    340:            if (pfi->nProps > 0)
                    341:            {
                    342:                *ppfp = (DIXFontPropPtr)Xalloc(sizeof(DIXFontProp)*pfi->nProps);
                    343:                if (*ppfp == NullDIXFontProp)
                    344:                    return(FALSE);
                    345:                bcopy((char *)pfont->pFP, (char *)*ppfp,
                    346:                    sizeof(DIXFontProp)*pfi->nProps);
                    347:            }
                    348:            return(TRUE);
                    349:        }
                    350: 
                    351:     /* have to read it off disk */
                    352:     if ((pf = FiOpenForRead(lenpname, ppathname)) == NullFID)
                    353:        return(FALSE);
                    354:     if ((FiRead(pfi, 1, sizeof(FontInfoRec), pf) != sizeof(FontInfoRec)) ||
                    355:        pfi->version1 != FONT_FILE_VERSION ||
                    356:        pfi->version2 != FONT_FILE_VERSION)
                    357:     {
                    358:         FiClose(pf);
                    359:         return(FALSE);
                    360:     }
                    361: 
                    362:     bytesskip = BYTESOFFONTINFO(pfi) - sizeof(FontInfoRec) + 
                    363:                BYTESOFCHARINFO(pfi) + BYTESOFGLYPHINFO(pfi);
                    364:     bytesprops = BYTESOFPROPINFO(pfi) + BYTESOFSTRINGINFO(pfi);
                    365: 
                    366:     temp = (FontPropPtr)Xalloc(max(bytesskip, bytesprops));
                    367:     *ppfp = (DIXFontProp *)Xalloc(pfi->nProps * sizeof(DIXFontProp));
                    368: 
                    369:     if ((!temp) ||
                    370:        (*ppfp == NullDIXFontProp) ||
                    371:        (FiRead((char *)temp, 1, bytesskip, pf) != bytesskip) ||
                    372:        (FiRead((char *)temp, 1, bytesprops, pf) != bytesprops))
                    373:     {
                    374:        Xfree((char *)*ppfp);
                    375:        *ppfp = NullDIXFontProp;
                    376:        Xfree((char *)temp);
                    377:         FiClose(pf);
                    378:         return(FALSE);
                    379:     }
                    380:     strings = (char *)&temp[pfi->nProps];
                    381:     pffp = temp;
                    382:     for (i=0, pdfp=(*ppfp); i<pfi->nProps; i++, pdfp++, pffp++)
                    383:     {
                    384:        pdfp->name = MakeAtom(
                    385:                &strings[pffp->name], strlen(&strings[pffp->name]), 1);
                    386:        if (pffp->indirect)
                    387:                pdfp->value = (INT32)MakeAtom(
                    388:                    &strings[pffp->value], strlen(&strings[pffp->value]), 1);
                    389:        else
                    390:                pdfp->value = pffp->value;
                    391:     }
                    392:     Xfree((char *)temp);
                    393:     FiClose(pf);
                    394:     return(TRUE);
                    395: }
                    396: 
                    397: 
                    398: #ifdef notdef
                    399: /*
                    400:  * assumes short is 2 bytes and long is 4, but nothing about padding
                    401:  */
                    402: #define _us    unsigned short
                    403: #define _ul    unsigned long
                    404: #define sw2( p)                \
                    405:        *((_us *)p) =   \
                    406:              *(_us *)p>>8      \
                    407:            | *(_us *)p<<8;
                    408: #define sw4( p)                \
                    409:        *((_ul *)p) =   \
                    410:              *(_ul *)p>>24     \
                    411:            | *(_ul *)p>>8 & 0x0000ff00 \
                    412:            | *(_ul *)p<<8 & 0x00ff0000 \
                    413:            | *(_ul *)p<<24;
                    414: 
                    415: #else
                    416: 
                    417: #define sw2( p) {      \
                    418:                int     t;      \
                    419:                t = ((char *)p)[0];     \
                    420:                ((char *)p)[0] = ((char *)p)[1];        \
                    421:                ((char *)p)[1] = t;     \
                    422:        }
                    423: #define sw4( p)        {       \
                    424:                int     t;      \
                    425:                t = ((char *)p)[0];     \
                    426:                ((char *)p)[0] = ((char *)p)[3];        \
                    427:                ((char *)p)[3] = t;     \
                    428:                t = ((char *)p)[1];     \
                    429:                ((char *)p)[1] = ((char *)p)[2];        \
                    430:                ((char *)p)[2] = t;     \
                    431:        }
                    432: 
                    433: #endif
                    434: 
                    435: void
                    436: QueryFont( pf, pr, nprotoxcistructs)
                    437:     FontPtr            pf;
                    438:     xQueryFontReply *  pr;     /* caller must allocate this storage */
                    439:     int                nprotoxcistructs;
                    440: {
                    441:     FontInfoPtr        pfi = pf->pFI;
                    442:     CharInfoPtr        pci;
                    443:     DIXFontProp *      pfp;
                    444:     int                ct;
                    445:     xFontProp *        prfp;
                    446:     xCharInfo *        prci;
                    447: 
                    448:     void       queryCharInfo();
                    449: 
                    450:     /* pr->length set in dispatch */
                    451:     pr->minCharOrByte2 = pfi->firstCol;
                    452:     pr->defaultChar = pfi->chDefault;
                    453:     pr->maxCharOrByte2 = pfi->lastCol;
                    454:     pr->drawDirection = pfi->drawDirection;
                    455:     pr->allCharsExist = pfi->allExist;
                    456:     pr->minByte1 = pfi->firstRow;
                    457:     pr->maxByte1 = pfi->lastRow;
                    458:     pr->fontAscent = pfi->fontAscent;
                    459:     pr->fontDescent = pfi->fontDescent;
                    460: 
                    461:     queryCharInfo( &pfi->minbounds, &pr->minBounds); 
                    462:     queryCharInfo( &pfi->maxbounds, &pr->maxBounds); 
                    463: 
                    464:     pr->nFontProps = pfi->nProps; 
                    465:     pr->nCharInfos = nprotoxcistructs; 
                    466: 
                    467: 
                    468:     for ( ct=0,
                    469:            pfp=pf->pFP,
                    470:            prfp=(xFontProp *)(&pr[1]);
                    471:          ct < pfi->nProps;
                    472:          ct++, pfp++, prfp++)
                    473:     {
                    474:        prfp->name = pfp->name;
                    475:        prfp->value = pfp->value;
                    476:     }
                    477: 
                    478:     for ( ct=0,
                    479:            pci = &pf->pCI[0],
                    480:            prci=(xCharInfo *)(prfp);
                    481:          ct<nprotoxcistructs;
                    482:          ct++, pci++, prci++)
                    483:        queryCharInfo( pci, prci);
                    484: }
                    485: 
                    486: /* static */ void
                    487: queryCharInfo( pci, pr)
                    488:     CharInfoPtr                pci;
                    489:     xCharInfo *                pr;     /* protocol packet to fill in */
                    490: {
                    491:     *pr = pci->metrics;
                    492: }
                    493: 
                    494: /* static */ void
                    495: SwapFont( pr, hasGlyphs)
                    496:     xQueryFontReply *  pr;
                    497:     Bool hasGlyphs;
                    498: {
                    499:     int                i;
                    500:     xCharInfo *        pxci;
                    501:     int                nchars, nprops;
                    502:     char       *pby;
                    503:     register char n;
                    504: 
                    505:     swaps(&pr->sequenceNumber, n);
                    506:     swapl(&pr->length, n);
                    507:     nchars = pr->nCharInfos;
                    508:     nprops = pr->nFontProps;
                    509:     SwapFontInfo(pr);
                    510:     pby = (char *) &pr[1];
                    511:     /* Font properties are an atom and either an int32 or a CARD32, so
                    512:      * they are always 2 4 byte values */
                    513:     for(i = 0; i < nprops; i++)
                    514:     {
                    515:        swapl(pby, n);
                    516:        pby += 4;
                    517:        swapl(pby, n);
                    518:        pby += 4;
                    519:     }
                    520:     if (hasGlyphs)
                    521:     {
                    522:        pxci = (xCharInfo *)pby;
                    523:        for(i = 0; i< nchars; i++, pxci++)
                    524:            SwapCharInfo(pxci);
                    525:     }
                    526: }
                    527: 
                    528: SwapFontInfo(pr)
                    529:     xQueryFontReply *pr;
                    530: {
                    531:     register char              n;
                    532: 
                    533:     swaps(&pr->minCharOrByte2, n);
                    534:     swaps(&pr->maxCharOrByte2, n);
                    535:     swaps(&pr->defaultChar, n);
                    536:     swaps(&pr->nFontProps, n);
                    537:     swaps(&pr->fontAscent, n);
                    538:     swaps(&pr->fontDescent, n);
                    539:     SwapCharInfo( &pr->minBounds);
                    540:     SwapCharInfo( &pr->maxBounds);
                    541:     swapl(&pr->nCharInfos, n);
                    542: }
                    543: SwapCharInfo(pInfo)
                    544:     xCharInfo  *pInfo;
                    545: {
                    546:     register char n;
                    547: 
                    548:     swaps(&pInfo->leftSideBearing, n);
                    549:     swaps(&pInfo->rightSideBearing, n);
                    550:     swaps(&pInfo->characterWidth, n);
                    551:     swaps(&pInfo->ascent, n);
                    552:     swaps(&pInfo->descent, n);
                    553:     swaps(&pInfo->attributes, n);
                    554: }
                    555: 
                    556: 
                    557: /* text support routines. A charinfo array builder, and a bounding */
                    558: /* box calculator */
                    559: 
                    560: void
                    561: GetGlyphs(font, count, chars, fontEncoding, glyphcount, glyphs)
                    562:     FontPtr font;
                    563:     int count;
                    564:     register unsigned char *chars;
                    565:     FontEncoding fontEncoding;
                    566:     unsigned int *glyphcount;  /* RETURN */
                    567:     CharInfoPtr glyphs[];      /* RETURN */
                    568: {
                    569:     CharInfoPtr                pCI = font->pCI;
                    570:     FontInfoPtr                pFI = font->pFI;
                    571:     unsigned int       firstCol = pFI->firstCol;
                    572:     unsigned int       numCols = pFI->lastCol - firstCol + 1;
                    573:     unsigned int       firstRow = pFI->firstRow;
                    574:     unsigned int       numRows = pFI->lastRow - firstRow + 1;
                    575:     unsigned int       chDefault = pFI->chDefault;
                    576:     register int       i;
                    577:     int                        n;
                    578:     register unsigned int      c;
                    579:     register CharInfoPtr       ci;
                    580: 
                    581:     n = 0;
                    582:     switch (fontEncoding) {
                    583: 
                    584:        case Linear8Bit:
                    585:        case TwoD8Bit:
                    586:            for (i=0; i < count; i++) {
                    587: 
                    588:                c = (*chars++) - firstCol;
                    589:                if (c < numCols) {
                    590:                    ci = &pCI[c];
                    591:                    if (ci->exists) {glyphs[n++] = ci; continue;}
                    592:                }
                    593: 
                    594:                c = chDefault - firstCol;
                    595:                if (c < numCols) {
                    596:                    ci = &pCI[c];
                    597:                    if (ci->exists) glyphs[n++] = ci;
                    598:                }
                    599:            }
                    600:            break;
                    601: 
                    602:        case Linear16Bit:
                    603:            for (i=0; i < count; i++) {
                    604: 
                    605:                chars++;
                    606:                c = (*chars++) - firstCol;
                    607:                if (c < numCols) {
                    608:                    ci = &pCI[c];
                    609:                    if (ci->exists) {glyphs[n++] = ci; continue;}
                    610:                }
                    611: 
                    612:                c = chDefault - firstCol;
                    613:                if (c < numCols) {
                    614:                    ci = &pCI[c];
                    615:                    if (ci->exists) glyphs[n++] = ci;
                    616:                }
                    617:            }
                    618:            break;
                    619: 
                    620:        case TwoD16Bit:
                    621:            for (i=0; i < count; i++) {
                    622:                register unsigned int row;
                    623:                register unsigned int col;
                    624: 
                    625:                row = (*chars++) - firstRow;
                    626:                col = (*chars++) - firstCol;
                    627:                if ((row < numRows) && (col < numCols)) {
                    628:                    c = row*numCols + col;
                    629:                    ci = &pCI[c];
                    630:                    if (ci->exists) {glyphs[n++] = ci; continue;}
                    631:                }
                    632: 
                    633:                row = (chDefault >> 8)-firstRow;
                    634:                col = (chDefault & 0xff)-firstCol;
                    635:                if ((row < numRows) && (col < numCols)) {
                    636:                    c = row*numCols + col;
                    637:                    ci = &pCI[c];
                    638:                    if (ci->exists) glyphs[n++] = ci;
                    639:                }
                    640:            }
                    641:            break;
                    642:     }
                    643:     *glyphcount = n;
                    644: }
                    645: 
                    646: 
                    647: 
                    648: void
                    649: QueryGlyphExtents(font, charinfo, count, info)
                    650:     FontPtr font;
                    651:     CharInfoPtr *charinfo;
                    652:     unsigned int count;
                    653:     ExtentInfoRec *info;
                    654: {
                    655:     int        i;
                    656: 
                    657:     info->drawDirection = font->pFI->drawDirection;
                    658: 
                    659:     info->fontAscent = font->pFI->fontAscent;
                    660:     info->fontDescent = font->pFI->fontDescent;
                    661: 
                    662:     if (count != 0) {
                    663: 
                    664:        info->overallAscent  = charinfo[0]->metrics.ascent;
                    665:        info->overallDescent = charinfo[0]->metrics.descent;
                    666:        info->overallLeft    = charinfo[0]->metrics.leftSideBearing;
                    667:        info->overallRight   = charinfo[0]->metrics.rightSideBearing;
                    668:        info->overallWidth   = charinfo[0]->metrics.characterWidth;
                    669: 
                    670:        for (i=1; i < count; i++) {
                    671:            info->overallAscent = max(
                    672:                info->overallAscent,
                    673:                charinfo[i]->metrics.ascent);
                    674:            info->overallDescent = max(
                    675:                info->overallDescent,
                    676:                charinfo[i]->metrics.descent);
                    677:            info->overallLeft = min(
                    678:                info->overallLeft,
                    679:                info->overallWidth+charinfo[i]->metrics.leftSideBearing);
                    680:            info->overallRight = max(
                    681:                info->overallRight,
                    682:                info->overallWidth+charinfo[i]->metrics.rightSideBearing);
                    683:            /* yes, this order is correct; overallWidth IS incremented last */
                    684:            info->overallWidth += charinfo[i]->metrics.characterWidth;
                    685:        }
                    686: 
                    687:     } else {
                    688: 
                    689:        info->overallAscent  = 0;
                    690:        info->overallDescent = 0;
                    691:        info->overallWidth   = 0;
                    692:        info->overallLeft    = 0;
                    693:        info->overallRight   = 0;
                    694: 
                    695:     }
                    696: }
                    697: 
                    698: void
                    699: QueryTextExtents(font, count, chars, info)
                    700:     FontPtr font;
                    701:     unsigned int count;
                    702:     unsigned short *chars;
                    703:     ExtentInfoRec *info;
                    704: {
                    705:     CharInfoPtr *charinfo =
                    706:        (CharInfoPtr *)ALLOCATE_LOCAL(count*sizeof(CharInfoPtr));
                    707:     unsigned int n;
                    708: 
                    709:     if(!charinfo)
                    710:        return;
                    711:     if (font->pFI->lastRow == 0)
                    712:        GetGlyphs(font, count, chars, Linear16Bit, &n, charinfo);
                    713:     else
                    714:        GetGlyphs(font, count, chars, TwoD16Bit, &n, charinfo);
                    715: 
                    716:     QueryGlyphExtents(font, charinfo, n, info);
                    717: 
                    718:     DEALLOCATE_LOCAL(charinfo);
                    719: }
                    720: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.