home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / x / volume5 / xldimage / part02 / send.c < prev    next >
Encoding:
C/C++ Source or Header  |  1989-11-13  |  4.2 KB  |  160 lines

  1. /* send.c:
  2.  *
  3.  * send an Image to an X pixmap
  4.  *
  5.  * jim frost 10.02.89
  6.  *
  7.  * Copyright 1989 Jim Frost.  See included file "copyright.h" for complete
  8.  * copyright information.
  9.  */
  10.  
  11. #include "copyright.h"
  12. #include "xloadimage.h"
  13.  
  14. unsigned int sendImageToX(disp, scrn, visual, image, pixmap, cmap, verbose)
  15.      Display      *disp;
  16.      int           scrn;
  17.      Visual       *visual;
  18.      Image        *image;
  19.      Pixmap       *pixmap;
  20.      Colormap     *cmap;
  21.      unsigned int  verbose;
  22. { Pixel        *index;
  23.   unsigned int  a, newmap, x, y;
  24.   byte         *pixptr;
  25.   XColor        xcolor;
  26.   XGCValues     gcv;
  27.   GC            gc;
  28.   XImage       *ximage;
  29.  
  30.   goodImage(image, "sendImageToX");
  31.  
  32.   switch(visual->class) {
  33.   case PseudoColor:
  34.   case GrayScale:
  35.   case StaticColor:
  36.   case StaticGray:
  37.     break;
  38.   default:
  39.     printf("sendImageToX: unsupported display visual\n");
  40.     exit(1);
  41.   }
  42.  
  43.   index= (Pixel *)lmalloc(sizeof(Pixel) * image->rgb.used);
  44.   xcolor.flags= DoRed | DoGreen | DoBlue;
  45.  
  46.   /* get the colormap to use
  47.    */
  48.  
  49.   if (visual == DefaultVisual(disp, scrn)) {
  50.     *cmap= DefaultColormap(disp, scrn);
  51.     newmap= 0;
  52.   }
  53.   else {
  54.     if ((visual->class == PseudoColor) || (visual->class == GrayScale))
  55.       *cmap= XCreateColormap(disp, scrn, AllocNone);
  56.     else
  57.       *cmap= XCreateColormap(disp, scrn, AllocAll);
  58.     newmap= 1;
  59.   }
  60.  
  61.   /* here's where we have fun; we try to build a reasonable colormap from
  62.    * whatever X will give us.  ugh.  blech.  gag.  puke.  barf.
  63.    */
  64.  
  65.   if ((visual->class == PseudoColor) || (visual->class == GrayScale)) {
  66.     for (a= 0; a < image->rgb.used; a++) {
  67.       if (! XAllocColorCells(disp, *cmap, False, NULL, 0, index + a, 1))
  68.     if (newmap)
  69.       break;
  70.     else {
  71.       *cmap= XCopyColormapAndFree(disp, *cmap);
  72.       newmap= 1;
  73.       a--;
  74.     }
  75.     }
  76.     if (a < image->rgb.used)     /* can't get enough colors, so reduce */
  77.       reduce(image, a, verbose); /* the colormap to fit what we have */
  78.     for (a= 0; a < image->rgb.used; a++) {
  79.       xcolor.pixel= *(index + a);
  80.       xcolor.red= *(image->rgb.red + a);
  81.       xcolor.green= *(image->rgb.green + a);
  82.       xcolor.blue= *(image->rgb.blue + a);
  83.       XStoreColor(disp, *cmap, &xcolor);
  84.     }
  85.   }
  86.   else if ((visual->class == StaticColor) || (visual->class == StaticGray)) {
  87.     for (a= 0; a < image->rgb.used; a++) {
  88.       xcolor.red= *(image->rgb.red + a);
  89.       xcolor.green= *(image->rgb.green + a);
  90.       xcolor.blue= *(image->rgb.blue + a);
  91.       if (! XAllocColor(disp, *cmap, &xcolor)) {
  92.     printf("sendImageToX: XAllocColor failed on StaticGrey visual\n");
  93.     return(0);
  94.       }
  95.       *(index + a)= xcolor.pixel;
  96.     }
  97.   }
  98.  
  99.   *pixmap= XCreatePixmap(disp, RootWindow(disp, scrn), image->width,
  100.              image->height, DefaultDepth(disp, scrn));
  101.  
  102.   /* blast the image across
  103.    */
  104.  
  105.   switch (image->type) {
  106.   case IBITMAP:
  107.     gcv.function= GXcopy;
  108.     gcv.foreground= *(index + 1);
  109.     gcv.background= *index;
  110.     gc= XCreateGC(disp, *pixmap, GCFunction | GCForeground | GCBackground,
  111.           &gcv);
  112.     ximage= XCreateImage(disp, visual, image->depth, XYBitmap, 0, image->data,
  113.              image->width, image->height, 8, 0);
  114.     ximage->bitmap_bit_order= MSBFirst;
  115.     ximage->byte_order= MSBFirst;
  116.     XPutImage(disp, *pixmap, gc, ximage, 0, 0, 0, 0,
  117.           image->width, image->height);
  118.     XFreeGC(disp, gc);
  119.     break;
  120.  
  121.   case IRGB:
  122.  
  123.     /* modify pixel values to fit the colormap
  124.      */
  125.  
  126.     if (verbose) {
  127.       printf("  Modifying image to conform to X colormap...");
  128.       fflush(stdout);
  129.     }
  130.     pixptr= image->data;
  131.     for (y= 0; y < image->height; y++)
  132.       for (x= 0; x < image->width; x++) {
  133.     valToMem(*(index + memToVal(pixptr, image->pixlen)),
  134.          pixptr, image->pixlen);
  135.     pixptr += image->pixlen;
  136.       }
  137.     if (verbose)
  138.       printf("done\n");
  139.  
  140.     gcv.function= GXcopy;
  141.     gc= XCreateGC(disp, *pixmap, GCFunction, &gcv);
  142.     ximage= XCreateImage(disp, visual, image->depth, ZPixmap, 0, image->data,
  143.              image->width, image->height, 8, 0);
  144.     ximage->byte_order= MSBFirst; /* trust me, i know what i'm talking about */
  145.  
  146.     XPutImage(disp, *pixmap, gc, ximage, 0, 0,
  147.           0, 0, image->width, image->height);
  148.     ximage->data= NULL;
  149.     XDestroyImage(ximage); /* waste not want not */
  150.     XFreeGC(disp, gc);
  151.     break;
  152.  
  153.   default:
  154.     printf("sendImageToX: bad image type\n");
  155.     return(0);
  156.   }
  157.   lfree(index);
  158.   return(1);
  159. }
  160.