home *** CD-ROM | disk | FTP | other *** search
/ The World of Computer Software / World_Of_Computer_Software-02-385-Vol-1of3.iso / x / xibm.zip / ppc / ppcGBlt.c < prev    next >
C/C++ Source or Header  |  1991-07-23  |  12KB  |  411 lines

  1. /*
  2.  * Copyright IBM Corporation 1987,1988,1989
  3.  *
  4.  * All Rights Reserved
  5.  *
  6.  * Permission to use, copy, modify, and distribute this software and its
  7.  * documentation for any purpose and without fee is hereby granted,
  8.  * provided that the above copyright notice appear in all copies and that 
  9.  * both that copyright notice and this permission notice appear in
  10.  * supporting documentation, and that the name of IBM not be
  11.  * used in advertising or publicity pertaining to distribution of the
  12.  * software without specific, written prior permission.
  13.  *
  14.  * IBM DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
  15.  * ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
  16.  * IBM BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
  17.  * ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
  18.  * WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
  19.  * ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
  20.  * SOFTWARE.
  21.  *
  22. */
  23.  
  24. /* Image Glyph Blt in terms of screen->rectFill and screen->glyphFill
  25.  * for ppc
  26.  *
  27.  *  Tom Paquin 9/87
  28.  *
  29.  */
  30.  
  31. /* $Header: /andrew/X11/r3src/r3plus/server/ddx/ibm/ppc/RCS/ppcGBlt.c,v 9.2 89/06/21 22:28:17 jeff Exp $ */
  32. /* $Source: /andrew/X11/r3src/r3plus/server/ddx/ibm/ppc/RCS/ppcGBlt.c,v $ */
  33.  
  34. #ifndef lint
  35. static char *rcsid = "$Header: /andrew/X11/r3src/r3plus/server/ddx/ibm/ppc/RCS/ppcGBlt.c,v 9.2 89/06/21 22:28:17 jeff Exp $";
  36. #endif
  37.  
  38.  
  39. #include    "X.h"
  40. #include    "Xmd.h"
  41. #include    "Xproto.h"
  42. #include    "font.h"
  43. #include    "misc.h"
  44. #include    "fontstruct.h"
  45. #include    "dixfontstr.h"
  46. #include    "gcstruct.h"
  47. #include    "windowstr.h"
  48. #include    "scrnintstr.h"
  49. #include    "pixmapstr.h"
  50. #include    "regionstr.h"
  51.  
  52. #include    "OScompiler.h"
  53.  
  54. #include    "ppc.h"
  55. #include    "ibmTrace.h"
  56.  
  57. extern PixmapPtr ppcCreatePixmap() ;
  58. extern int mfbGCPrivateIndex;
  59.  
  60. void
  61. filltempPixmap( pPixmap, pglyph, w, h )
  62.      PixmapPtr pPixmap ;
  63. register unsigned char *pglyph ;
  64. register const int w ;
  65. register int h ;
  66. {
  67. register unsigned char *dest = pPixmap->devPrivate.ptr;
  68. register int        dstWidth= pPixmap->devKind;
  69.  
  70. while ( h-- ) {
  71.     MOVE( pglyph, dest, w ) ;
  72.     pglyph += w ;
  73.     dest += dstWidth;
  74. }
  75.  
  76. return ;
  77. }
  78.  
  79. void
  80. ppcImageGlyphBlt( pDrawable, pGC, x, y, nglyph, ppci, pglyphBase )
  81.     DrawablePtr pDrawable ;
  82.     GC         *pGC ;
  83.     int     x, y ;
  84.     unsigned int nglyph ;
  85.     CharInfoPtr *ppci ;        /* array of character info */
  86.     unsigned char *pglyphBase ;    /* start of array of glyphs */
  87. {
  88.     register unsigned char    *pglyph ;
  89.     register BoxPtr        pbox ;
  90.     register int        nbox ;
  91.     ExtentInfoRec         info ;    
  92.     BoxRec             bbox ;    
  93.     xRectangle             backrect ;
  94.     CharInfoPtr          pci ;
  95.     FontInfoPtr            pfi ;
  96.     int             fg, bg, pm, ax,ay,zx,zy,zw,zh,
  97.                     w, h, widthGlyph ;
  98.  
  99.     RegionPtr             pRegion ;
  100.  
  101.     PixmapPtr            pTempPixmap = NULL ;
  102.     ScreenPtr            pScreen ;
  103.     ppcScrnPriv            *pScrPriv ;
  104.     int                been_here = FALSE ;
  105.     void            (*rectFunc)(), (*glyphFunc)(), (*stipFunc)() ;
  106.     int                CursorIsSaved ;
  107.  
  108.     if ( pDrawable->type == DRAWABLE_PIXMAP ) {
  109.     miImageGlyphBlt( pDrawable, pGC, x, y, nglyph, ppci, pglyphBase ) ;
  110.     return ;
  111.     }
  112.  
  113.     pRegion = ((ppcPrivGC *)(pGC->devPrivates[mfbGCPrivateIndex].ptr))->pCompositeClip ; 
  114.     if ( !( nbox = REGION_NUM_RECTS(pRegion) ) )
  115.     return ;
  116.  
  117.     pScreen = pGC->pScreen ;
  118.     pScrPriv = (ppcScrnPriv *) pScreen->devPrivate ;
  119.     pfi = &pGC->font->info;
  120.  
  121.     rectFunc = pScrPriv->solidFill ;
  122.     stipFunc = pScrPriv->stipFill ;
  123.     glyphFunc = pScrPriv->glyphFill ;
  124.  
  125.     QueryGlyphExtents(pGC->font, ppci, nglyph, &info) ;
  126.  
  127.     x += pDrawable->x ;
  128.     y += pDrawable->y ;
  129.  
  130.     backrect.y = y - pfi->fontAscent ;
  131.     backrect.height = pfi->fontAscent + pfi->fontDescent ;
  132.     backrect.width =
  133.      MAX( ( info.overallRight - info.overallLeft ), info.overallWidth ) ;
  134.     backrect.x = x + info.overallLeft ;
  135.  
  136.     /* High Level Software Cursor Support */
  137.     CursorIsSaved = !(*(pScrPriv->CursorSemaphore))
  138.          && (* pScrPriv->CheckCursor)( backrect.x, backrect.y,
  139.                            backrect.width,
  140.                            backrect.height ) ;
  141.     (*(pScrPriv->CursorSemaphore))++ ;
  142.  
  143.     bbox.x1 = x + info.overallLeft ;
  144.     bbox.x2 = x + info.overallRight ;
  145.     bbox.y1 = y - info.overallAscent ;
  146.     bbox.y2 = y + info.overallDescent ;
  147.  
  148.     pm =  pGC->planemask ;
  149.     bg =  pGC->bgPixel ;
  150.     for ( pbox = REGION_RECTS(pRegion) ; nbox-- ; pbox++ ) {
  151.     ax = MAX( pbox->x1, backrect.x ) ;
  152.     ay = MAX( pbox->y1, backrect.y ) ;
  153.     zx = MIN( pbox->x2, backrect.x + backrect.width ) ;
  154.     zy = MIN( pbox->y2, backrect.y + backrect.height ) ;
  155.     if ( ( ( zw = zx - ax ) > 0 ) && ( ( zh = zy - ay ) > 0 ) )
  156.         (* rectFunc)( bg, GXcopy, pm, ax, ay, zw, zh ) ;
  157.     }
  158.  
  159.     fg =  pGC->fgPixel ;
  160.  
  161.     switch ( (* pScreen->RectIn)( pRegion, &bbox ) ) {
  162.       case rgnIN:
  163.         while ( nglyph-- ) {
  164.         pci = *ppci++ ;
  165.         pglyph = pci->bits;
  166.         if ( ( w = GLYPHWIDTHPIXELS(pci) )
  167.           && ( h = GLYPHHEIGHTPIXELS(pci) ) )
  168.             (*glyphFunc)( pglyph,
  169.                   x + pci->metrics.leftSideBearing,
  170.                   y - pci->metrics.ascent,
  171.                   w, h, fg, GXcopy, pm ) ;
  172.         x += pci->metrics.characterWidth ;    /* update character origin */
  173.         } /* while nglyph-- */
  174.       case rgnOUT:
  175.     break ;
  176.       case rgnPART:
  177.       {
  178.     RegionPtr prgnClip ;
  179.  
  180.     BoxRec cbox ;
  181.     int glx, gly ;
  182.  
  183.         while ( nglyph-- )
  184.         {
  185.         pci = *ppci++ ;
  186.         pglyph = pci->bits;
  187.         w = GLYPHWIDTHPIXELS(pci) ;
  188.         h = GLYPHHEIGHTPIXELS(pci) ;
  189.         cbox.x1 = glx = x + pci->metrics.leftSideBearing ;
  190.         cbox.x2 = cbox.x1 + w ;
  191.         cbox.y1 = gly = y - pci->metrics.ascent ;
  192.         cbox.y2 = cbox.y1 + h ;
  193.  
  194.         switch ( (* pScreen->RectIn)( pRegion,  &cbox ) ) {
  195.           case rgnIN:
  196.             (* glyphFunc)( pglyph, glx, gly, w, h, fg, GXcopy, pm ) ;
  197.           case rgnOUT:
  198.         break ;
  199.           case rgnPART:
  200.         if ( !been_here )
  201.             {
  202.             widthGlyph = pfi->maxbounds.rightSideBearing-
  203.                         pfi->minbounds.leftSideBearing;
  204.             widthGlyph = PADGLYPHWIDTHBYTES(widthGlyph);
  205.                 pTempPixmap = ppcCreatePixmap( pScreen, widthGlyph * 8,
  206.                 pfi->maxbounds.ascent + pfi->maxbounds.descent, 1);
  207.             been_here = TRUE;
  208.             }
  209.         prgnClip = (* pScreen->RegionCreate)( &cbox,
  210.                               REGION_NUM_RECTS(pRegion)) ;
  211.         (* pScreen->Intersect)( prgnClip, prgnClip, pRegion ) ;
  212.         if ( !( nbox = REGION_NUM_RECTS(prgnClip) ) ) {
  213.             (* pScreen->RegionDestroy)( prgnClip ) ;
  214.             break ;
  215.         }
  216.         widthGlyph = GLYPHWIDTHBYTESPADDED(pci) ;
  217.             filltempPixmap(pTempPixmap, pglyph, widthGlyph, h) ;
  218.         for ( pbox = REGION_RECTS(prgnClip) ; nbox-- ; pbox++ )
  219.             {
  220.             ax = MAX(pbox->x1, cbox.x1) ;
  221.             ay = MAX(pbox->y1, cbox.y1) ;
  222.             zx = MIN(pbox->x2, cbox.x2) ;
  223.             zy = MIN(pbox->y2, cbox.y2) ;
  224.                 if ( ( ( zw = zx - ax ) > 0 )
  225.                   && ( ( zh = zy - ay ) > 0 ) )
  226.                 (*stipFunc)( pTempPixmap, 
  227.                          fg, GXcopy, pm, ax, ay,
  228.                          zw, zh, glx, gly ) ;
  229.             }
  230.         (* pScreen->RegionDestroy)( prgnClip ) ;
  231.         break ;
  232.         }
  233.         /* update character origin */
  234.         x += pci->metrics.characterWidth ;
  235.         } /* while nglyph-- */
  236.  
  237.     if ( pTempPixmap )
  238.         (* pScreen->DestroyPixmap)( pTempPixmap ) ;
  239.  
  240.       }
  241.       default:
  242.     break ;
  243.     }
  244.     if ( !--(*(pScrPriv->CursorSemaphore)) && CursorIsSaved )
  245.     (* pScrPriv->ReplaceCursor)() ;
  246.  
  247.     return ;
  248. }
  249.  
  250. void
  251. ppcPolyGlyphBlt( pDrawable, pGC, x, y, nglyph, ppci, pglyphBase )
  252.     DrawablePtr pDrawable ;
  253.     GC         *pGC ;
  254.     int     x, y ;
  255.     unsigned int nglyph ;
  256.     CharInfoPtr *ppci ;        /* array of character info */
  257.     unsigned char *pglyphBase ;    /* start of array of glyphs */
  258. {
  259.     register unsigned char    *pglyph ;
  260.     register BoxPtr        pbox ;
  261.     register int        nbox ;
  262.     ExtentInfoRec         info ;    
  263.     BoxRec             bbox ;    
  264.  
  265.     CharInfoPtr          pci ;
  266.     FontInfoPtr            pfi ;
  267.     int             fg, alu, pm, ax,ay,zx,zy,zw,zh,
  268.                     w, h, widthGlyph ;
  269.  
  270.     RegionPtr             pRegion ;
  271.  
  272.     PixmapPtr            pTempPixmap = NULL ;
  273.     ScreenPtr            pScreen ;
  274.     ppcScrnPriv            *pScrPriv ;
  275.     int                been_here = FALSE ;
  276.     void            (*glyphFunc)(), (*stipFunc)() ;
  277.     int                CursorIsSaved ;
  278.  
  279.     if ( pDrawable->type == DRAWABLE_PIXMAP ) {
  280.     miPolyGlyphBlt( pDrawable, pGC, x, y, nglyph, ppci, pglyphBase ) ;
  281.     return ;
  282.     }
  283.  
  284.     if ( ( (ppcPrivGC *) pGC->devPrivates[mfbGCPrivateIndex].ptr)->colorRrop.fillStyle != FillSolid ) {
  285.     miPolyGlyphBlt(pDrawable, pGC, x, y, nglyph, ppci, pglyphBase) ;
  286.     return ;
  287.     }
  288.  
  289.     pRegion = ((ppcPrivGC *)(pGC->devPrivates[mfbGCPrivateIndex].ptr))->pCompositeClip ; 
  290.     if ( !( nbox = REGION_NUM_RECTS(pRegion)) )
  291.     return ;
  292.  
  293.     pScreen = pGC->pScreen ;
  294.     pScrPriv = (ppcScrnPriv *) pScreen->devPrivate ;
  295.     pfi = &pGC->font->info;
  296.  
  297.     stipFunc = pScrPriv->stipFill ;
  298.     glyphFunc = pScrPriv->glyphFill ;
  299.  
  300.     QueryGlyphExtents(pGC->font, ppci, nglyph, &info) ;
  301.  
  302.     x += pDrawable->x ;
  303.     y += pDrawable->y ;
  304.  
  305.     bbox.x1 = x + info.overallLeft ;
  306.     bbox.x2 = x + info.overallRight ;
  307.     bbox.y1 = y - info.overallAscent ;
  308.     bbox.y2 = y + info.overallDescent ;
  309.  
  310.     /* High Level Software Cursor Support */
  311.     CursorIsSaved = !(*(pScrPriv->CursorSemaphore))
  312.          && (* pScrPriv->CheckCursor)( bbox.x1, bbox.y1,
  313.                            info.overallRight
  314.                          - info.overallLeft,
  315.                            info.overallAscent
  316.                          + info.overallDescent ) ;
  317.     (*(pScrPriv->CursorSemaphore))++ ;
  318.  
  319.     pbox = REGION_RECTS(pRegion) ;
  320.  
  321.     /* Use Reduced Raster-Op */
  322.     alu = ( (ppcPrivGC *) pGC->devPrivates[mfbGCPrivateIndex].ptr)->colorRrop.alu ;
  323.     pm =  ( (ppcPrivGC *) pGC->devPrivates[mfbGCPrivateIndex].ptr)->colorRrop.planemask ;
  324.     fg =  ( (ppcPrivGC *) pGC->devPrivates[mfbGCPrivateIndex].ptr)->colorRrop.fgPixel ;
  325.  
  326.     switch ( (* pScreen->RectIn)( pRegion, &bbox ) ) {
  327.       case rgnOUT:
  328.     break ;
  329.       case rgnIN:
  330.         while (nglyph-- )
  331.         {
  332.         pci = *ppci++ ;
  333.         pglyph = pci->bits;
  334.         if ( ( w = GLYPHWIDTHPIXELS(pci) )
  335.           && ( h = GLYPHHEIGHTPIXELS(pci) ) )
  336.             (* glyphFunc)( pglyph,
  337.                    x + pci->metrics.leftSideBearing,
  338.                    y - pci->metrics.ascent,
  339.                    w, h, fg, alu, pm ) ;
  340.         x += pci->metrics.characterWidth ;    /* update character origin */
  341.         } /* while nglyph-- */
  342.     break ;
  343.       case rgnPART:
  344.       {
  345.     RegionPtr prgnClip ;
  346.  
  347.     BoxRec cbox ;
  348.     int glx, gly ;
  349.  
  350.         while ( nglyph-- ) {
  351.         pci = *ppci++ ;
  352.         pglyph = pci->bits;
  353.         w = GLYPHWIDTHPIXELS(pci) ;
  354.         h = GLYPHHEIGHTPIXELS(pci) ;
  355.         cbox.x1 = glx = x + pci->metrics.leftSideBearing ;
  356.         cbox.y1 = gly = y - pci->metrics.ascent ;
  357.         cbox.x2 = cbox.x1 + w ;
  358.         cbox.y2 = cbox.y1 + h ;
  359.  
  360.         switch ( (* pScreen->RectIn)( pRegion,  &cbox ) ) {
  361.           case rgnIN:
  362.             (* glyphFunc)( pglyph, glx, gly, w, h, fg, alu, pm ) ;
  363.           case rgnOUT:
  364.         break ;
  365.           case rgnPART:
  366.         if ( !been_here ) {
  367.             widthGlyph= pfi->maxbounds.rightSideBearing-
  368.                     pfi->maxbounds.leftSideBearing;
  369.             widthGlyph= PADGLYPHWIDTHBYTES(widthGlyph);
  370.                 pTempPixmap = ppcCreatePixmap(pScreen, widthGlyph*8,
  371.                 pfi->maxbounds.ascent + pfi->maxbounds.descent, 
  372.                 1);
  373.             been_here = TRUE ;
  374.         }
  375.         prgnClip = (*pScreen->RegionCreate)(&cbox,REGION_NUM_RECTS(pRegion)) ;
  376.         (*pScreen->Intersect) (prgnClip, prgnClip, pRegion) ;
  377.         if ( !( nbox = REGION_NUM_RECTS(prgnClip) ) ) {
  378.             (* pScreen->RegionDestroy)( prgnClip ) ;
  379.             break ;
  380.         }
  381.         widthGlyph = GLYPHWIDTHBYTESPADDED(pci) ;
  382.             filltempPixmap( pTempPixmap, pglyph, widthGlyph, h ) ;
  383.         for ( pbox = REGION_RECTS(prgnClip) ; nbox-- ; pbox++ ) {
  384.             ax = MAX(pbox->x1, cbox.x1) ;
  385.             ay = MAX(pbox->y1, cbox.y1) ;
  386.             zx = MIN(pbox->x2, cbox.x2) ;
  387.             zy = MIN(pbox->y2, cbox.y2) ;
  388.             if ( ( ( zw = zx - ax ) > 0 )
  389.               && ( ( zh = zy - ay ) > 0 ) )
  390.                 (*stipFunc)(pTempPixmap, 
  391.                     fg, alu, pm, ax, ay, zw, zh,
  392.                     glx, gly) ;
  393.         }
  394.         (* pScreen->RegionDestroy)( prgnClip ) ;
  395.         break ;
  396.         }
  397.         /* update character origin */
  398.         x += pci->metrics.characterWidth ;
  399.         } /* while nglyph-- */
  400.     if ( pTempPixmap )
  401.         (* pScreen->DestroyPixmap)( pTempPixmap ) ;
  402.       }
  403.       default:
  404.     break ;
  405.     }
  406.     if ( !--(*(pScrPriv->CursorSemaphore)) && CursorIsSaved )
  407.     (* pScrPriv->ReplaceCursor)() ;
  408.  
  409.     return ;
  410. }
  411.