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

  1. /**/
  2. #include "X.h"
  3. #include "gcstruct.h"
  4. #include "pixmapstr.h"
  5. #include "windowstr.h"
  6. #include "scrnintstr.h"
  7. #include "servermd.h"
  8. #include "mi.h"
  9. #include "ppc.h"
  10.  
  11. #include "mpel.h"
  12. #include "mpelFifo.h"
  13.  
  14. #include "ibmTrace.h"
  15.  
  16. extern int mfbGCPrivateIndex;
  17.  
  18. extern void mpel4x4();    /* This is also used by cursor code */
  19.  
  20. /* Put Image optimized for megapel
  21.  * (partially stolen from cfbPutImage)
  22.  */
  23.  
  24. void mpelPutImage(pDrawable, pGC, depth, x, y, w, h, leftPad, format, pImage)
  25. DrawablePtr    pDrawable;
  26. GCPtr        pGC;
  27. unsigned int    depth, w, h, format;
  28. int        x, y, leftPad;
  29. unsigned char    *pImage;
  30. {
  31.   unsigned int nbytes;
  32.   ppcPrivGC *pPriv;
  33.   BoxRec b;
  34.   int inters;
  35.   RegionPtr pRegion;
  36.  
  37.   if(w == 0 || h == 0)
  38.     return;
  39.  
  40.   b.x1 = pDrawable->x + x;
  41.   b.x2 = pDrawable->x + x + w - 1;
  42.   b.y1 = pDrawable->y + y;
  43.   b.y2 = pDrawable->y + y + h - 1;
  44.  
  45.   pPriv = (ppcPrivGC *)pGC->devPrivates[mfbGCPrivateIndex].ptr;
  46.   pRegion = pPriv->pCompositeClip;
  47.  
  48.   if(REGION_NIL(pRegion))
  49.     return;
  50.  
  51.   inters = miRectIn(pRegion, &b);
  52.  
  53.   if(inters == rgnOUT)
  54.     return;
  55.  
  56.   if(pDrawable->type == DRAWABLE_PIXMAP || format == XYPixmap || 
  57.      inters == rgnPART || pDrawable->y + h + 4 > MPEL_HEIGHT)
  58.     {
  59.       miPutImage(pDrawable, pGC, depth, x, y, w, h, leftPad, format, pImage);
  60.       return;
  61.     }
  62.  
  63.   /* After here, it is known that the image destination is unclipped */
  64.  
  65.   nbytes = (w * h * depth + 15) / 8;
  66.   nbytes &= ~1;
  67.  
  68.   TRACE(("mpelPutImage(... %d, %d, %d, %d, %d ...) nbytes %d\n",
  69.      x, y, w, h, leftPad, nbytes));
  70.  
  71.   /* If the image is larger than the max request size, use the slow method */
  72.   if (depth > 1 || nbytes > 32700)
  73.     {
  74.       int saveexp;
  75.       PixmapRec pm;
  76.       pm.drawable.type = DRAWABLE_PIXMAP;
  77.       pm.drawable.class = 0;
  78.       pm.drawable.pScreen = pDrawable->pScreen;
  79.       pm.drawable.bitsPerPixel = pm.drawable.depth = depth;
  80.       pm.drawable.id = 0;
  81.       pm.drawable.serialNumber = NEXT_SERIAL_NUMBER;
  82.       pm.drawable.x = pm.drawable.y = 0;
  83.       pm.drawable.width = w + leftPad;
  84.       pm.drawable.height = h;
  85.       pm.devKind = PixmapBytePad(pm.drawable.width, depth);
  86.       pm.refcnt = 1;
  87.       pm.devPrivate.ptr = (pointer)pImage;
  88.       saveexp = pPriv->fExpose;
  89.       ((ppcPrivGC *)pGC->devPrivates[mfbGCPrivateIndex].ptr)->fExpose = 0;
  90.       if (format == ZPixmap)
  91.     (void) (*pGC->ops->CopyArea)(&pm, pDrawable, pGC, leftPad, 0, w, h, x, y);
  92.       else
  93.     (void) (*pGC->ops->CopyPlane)(&pm, pDrawable, pGC, leftPad, 0, w, h, x, y, 1);
  94.       pPriv->fExpose = saveexp;
  95.     } else {
  96.       short *fbits;    /* data formatted for megapel adapter */
  97.       int dw, dh, adj;
  98.       mpelRectangle r;
  99.       mpelBLTImmed4x4WColorExpansion cmd;
  100.  
  101.       dw = (w + 7) & ~7;
  102.       dh = (h + 7) & ~7;
  103.       nbytes = dw * dh / 8;
  104.  
  105.       /* adj is the amount by which the destination area must be
  106.     moved to compensate for mpel4x4 padding the bottom edge 
  107.       of the image with blanks */
  108.       adj = (4 - (h & 3)) & 3;
  109.  
  110.       fbits = ALLOCATE_LOCAL(nbytes);
  111.  
  112.       bzero(fbits, nbytes);
  113.       mpel4x4(pImage, w, h, fbits);
  114.  
  115.       /* Must keep LLC (based on orignal h) */
  116.  
  117.       r.lleft.x = cmd.dest.lleft.x  = pDrawable->x + x;
  118.       r.lleft.y = MPEL_HEIGHT - pDrawable->y - y - h;
  119.       cmd.dest.lleft.y = r.lleft.y - adj;
  120.       r.uright.x = pDrawable->x + x + w - 1;
  121.       cmd.dest.uright.x = pDrawable->x + x + dw - 1;
  122.       cmd.dest.uright.y = MPEL_HEIGHT - pDrawable->y - y - h + dh - 1 - adj;
  123.       r.uright.y = MPEL_HEIGHT - pDrawable->y - 1;
  124.       cmd.color = pGC->fgPixel;
  125.       TRACE(("\t{%d,%d},{%d,%d}\n",
  126.          cmd.dest.lleft.x, cmd.dest.lleft.y,
  127.          cmd.dest.uright.x, cmd.dest.uright.y));
  128.       MPELBLTImmed4x4WColorExpansion(nbytes, &cmd);
  129.       MPELSendData(nbytes, fbits);
  130.  
  131.       DEALLOCATE_LOCAL(fbits);
  132.     }
  133. }
  134.  
  135.  
  136. /* Take a pointer to bitmap data, and format it into a set of 4x4 blocks
  137.  * suitable for use with mpel blt vpm 4x4 w/ color expansion.
  138.  *
  139.  * bits -- source data
  140.  * dst  -- where to put formatted bits (round up size to multiple of 4)
  141.  * sw, sh -- source dimensions
  142.  */
  143.  
  144. union i4c { unsigned int i;
  145.         unsigned char c[4];
  146.       };
  147. #define EXT(dst, i) *dst ++ = ((i & 0xf0000000) >> 16) | ((i & 0x00f00000) >> 12) | ((i & 0x0000f000) >> 8) | ((i & 0x000000f0) >> 4);\
  148.   *dst++ = ((i & 0x0f000000) >> 12) | ((i & 0x000f0000) >> 8) | ((i & 0x00000f00) >> 4) | (i & 0x0000000f);
  149.  
  150. void mpel4x4(bits, sw, sh, dst)
  151. char *bits;
  152. short *dst;
  153. int sw, sh;
  154. {
  155.   int dw = (sw + 7) & ~7;
  156.   int dh = (sh + 7) & ~7;
  157.   int xc, yc;
  158.   int src_al = ((sw + 7) / 8 + 3) & ~3;
  159.  
  160.  
  161.   TRACE(("mpel4x4(%#x, %d, %d, %#x) src_al %d dw %d dh %d\n",
  162.      bits, sw, sh, dst, src_al, dw, dh));
  163.  
  164.   if(sh & 3)
  165.     {
  166.       yc = (sh & ~3);
  167.       for(xc = 0; xc < (dw >> 3); xc++)
  168.     {
  169.       register unsigned int i;
  170.       register int yoff = yc * src_al;
  171.       union i4c u;
  172.       u.i = 0;
  173.       
  174.       switch(sh & 3)
  175.         {
  176.         case 3:
  177.         /* *(bits + xc + (yc + 2) * src_al) */
  178.           u.c[2] = *(bits + xc + yoff + src_al + src_al);
  179.         case 2:
  180.         /* *(bits + xc + (yc + 1) * src_al) */
  181.           u.c[1] = *(bits + xc + yoff + src_al);
  182.         case 1:
  183.           u.c[0] = *(bits + xc + yoff);
  184.         }
  185.       i = u.i;
  186.       EXT(dst, i)
  187.     }
  188.     }
  189.   for(yc = (sh-4)&~3; yc >= 0; yc -= 4)
  190.     {
  191.       for(xc = 0; xc < (dw>>3); xc++)
  192.     {
  193.       register unsigned int i;
  194.       union i4c u;
  195.       
  196.       u.c[0] = *(bits + xc + yc * src_al);
  197.       u.c[1] = *(bits + xc + (yc + 1) * src_al);
  198.       u.c[2] = *(bits + xc + (yc + 2) * src_al);
  199.       u.c[3] = *(bits + xc + (yc + 3) * src_al);
  200.       i = u.i;
  201.       EXT(dst, i)
  202.     }
  203.     }
  204. }
  205.  
  206.