123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871 |
- /*
- * CDE - Common Desktop Environment
- *
- * Copyright (c) 1993-2012, The Open Group. All rights reserved.
- *
- * These libraries and programs are free software; you can
- * redistribute them and/or modify them under the terms of the GNU
- * Lesser General Public License as published by the Free Software
- * Foundation; either version 2 of the License, or (at your option)
- * any later version.
- *
- * These libraries and programs are distributed in the hope that
- * they will be useful, but WITHOUT ANY WARRANTY; without even the
- * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
- * PURPOSE. See the GNU Lesser General Public License for more
- * details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with these libraries and programs; if not, write
- * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
- * Floor, Boston, MA 02110-1301 USA
- */
- /* $XConsortium: ilreadX.c /main/3 1995/10/23 15:59:17 rswiston $ */
- /**---------------------------------------------------------------------
- ***
- *** (c)Copyright 1991 Hewlett-Packard Co.
- ***
- *** RESTRICTED RIGHTS LEGEND
- *** Use, duplication, or disclosure by the U.S. Government is subject to
- *** restrictions as set forth in sub-paragraph (c)(1)(ii) of the Rights in
- *** Technical Data and Computer Software clause in DFARS 252.227-7013.
- *** Hewlett-Packard Company
- *** 3000 Hanover Street
- *** Palo Alto, CA 94304 U.S.A.
- *** Rights for non-DOD U.S. Government Departments and Agencies are as set
- *** forth in FAR 52.227-19(c)(1,2).
- ***
- ***-------------------------------------------------------------------*/
- #include "ilint.h"
- #include "ilcontext.h"
- #include "ilX.h"
- #include <math.h>
- #include <X11/Xutil.h>
- #include "ilpipelem.h"
- #include "ilerrors.h"
- /* Bit-flip table, in /ilc/ildata.c */
- extern const unsigned char ilBitReverseTable [];
- /* Private data for all ilReadXDrawable() pipe functions. */
- typedef struct {
- Display *display; /* copy of X display ptr */
- Drawable drawable; /* given to / derived by ilReadXDrawable() */
- Visual *visual; /* ptr to visual or null if a bitmap */
- Colormap colormap; /* ptr to colormap or null if a bitmap */
- int colormapSize; /* # of entries in the colormap */
- unsigned short *pPalette; /* palette for Pseudo/StaticColor or null */
- ilClientImage grayMapImage; /* ilMap() image for gray or null */
- ilPtr pGrayMapPixels; /* ptr to pixels in grayMapImage if non-null */
- ilBool isLongImage; /* long/pixel format (24 bit drawable) */
- ilClientImage rgbMapImage; /* ilMap() image for rgb or null */
- ilPtr pRGBMapPixels; /* ptr to pixels in rgbMapImage if non-null */
- ilRect rect; /* piece of X image to read */
- long stripHeight; /* height of each piece of drawable to read */
- int copyPixmapDepth; /* depth for copyPixmap, or 0 => don't create */
- Pixmap copyPixmap; /* pixmap to copy to/GetImage() from or null */
- GC copyGC; /* GC to use to copy to "copyPixmap" */
- int nRedOnes;
- int nGreenOnes;
- int nBlueOnes;
- int nRedZeros;
- int nGreenZeros;
- int nBlueZeros;
- Bool SlowMode;
- int OrgRedMask;
- int OrgGreenMask;
- int OrgBlueMask;
- } ilReadXPrivRec, *ilReadXPrivPtr;
- /* ------------------------ ilReadXInit ------------------------------- */
- /* Init() function for ilReadXDrawable() pipe elements.
- */
- static ilError ilReadXInit (
- ilReadXPrivPtr pPriv,
- ilImageInfo *pSrcImage,
- ilImageInfo *pDstImage
- )
- {
- #define NCOLORS 256
- #define NGRAYS 256
- #define NRGBS 256
- ilReadXPrivRec priv;
- /* Init the palette if present by querying the colormap, with # entries =
- pPriv->colormapSize (limit to NCOLORS; may be less, so init unused to black).
- */
- if (pPriv->pPalette) {
- int i;
- XColor cells [NCOLORS], *pColor;
- unsigned short *pPalette;
- for (i = 0, pColor = cells; i < NCOLORS; i++, pColor++) {
- pColor->red = pColor->green = pColor->blue = 0;
- pColor->pixel = i;
- }
- XQueryColors (pPriv->display, pPriv->colormap, cells,
- (pPriv->colormapSize > NCOLORS) ? NCOLORS : pPriv->colormapSize);
- for (i = 0, pPalette = pPriv->pPalette, pColor = cells; i < NCOLORS;
- i++, pPalette++, pColor++) {
- pPalette[0*256] = pColor->red;
- pPalette[1*256] = pColor->green;
- pPalette[2*256] = pColor->blue;
- }
- }
- /* If a grayMapImage, reading from grayscale: query the colormap and store
- the upper 8 bits of the green value into grayMapImage, which is used
- by an ilMap() filter which follows the ilReadXDrawable() (added there).
- */
- else if (pPriv->grayMapImage) {
- int i;
- XColor cells [NGRAYS], *pColor;
- ilPtr pByte;
- for (i = 0, pColor = cells; i < NGRAYS; i++, pColor++) {
- pColor->red = pColor->green = pColor->blue = 0;
- pColor->pixel = i;
- }
- XQueryColors (pPriv->display, pPriv->colormap, cells,
- (pPriv->colormapSize > NGRAYS) ? NGRAYS : pPriv->colormapSize);
- for (i = 0, pByte = pPriv->pGrayMapPixels, pColor = cells; i < NGRAYS;
- i++, pColor++)
- *pByte++ = pColor->green >> 8;
- }
- /* If an rgbMapImage, reading from True/DirectColor: query color - RGBs are
- independent. Init the mapImage which is 3 byte (rgb) per pixel.
- */
- else if (pPriv->rgbMapImage) {
- int i;
- XColor cells [NRGBS], *pColor;
- ilPtr pByte;
- for (i = 0, pColor = cells; i < NRGBS; i++, pColor++) {
-
- if(!(pPriv->SlowMode)){
- pColor->red = pColor->green = pColor->blue = 0;
- pColor->pixel = ((i << 16) | (i << 8) | i);
- }
- else {
-
- pColor->red = pColor->green = pColor->blue = 0;
- pColor->pixel = ((i << pPriv->nRedZeros) | (i << pPriv->nGreenZeros) |
- i << pPriv->nBlueZeros);
- }
- }
- XQueryColors (pPriv->display, pPriv->colormap, cells,
- (pPriv->colormapSize > NRGBS) ? NRGBS : pPriv->colormapSize);
- for (i = 0, pByte = pPriv->pRGBMapPixels, pColor = cells; i < NRGBS;
- i++, pColor++) {
- *pByte++ = pColor->red >> 8;
- *pByte++ = pColor->green >> 8;
- *pByte++ = pColor->blue >> 8;
- }
- }
- /* Create copyPixmap if required (copyPixmapDepth != 0).
- */
- if (pPriv->copyPixmapDepth) {
- pPriv->copyPixmap = XCreatePixmap (pPriv->display, pPriv->drawable, pPriv->rect.width,
- pPriv->stripHeight, pPriv->copyPixmapDepth);
- if (!pPriv->copyPixmap)
- return IL_ERROR_X_RESOURCE;
- }
- return IL_OK;
- }
- /* ------------------------ ilReadXCleanup ------------------------------- */
- /* Cleanup() function for ilReadXDrawable() pipe elements.
- Free anything in private that was created by Init().
- */
- static ilError ilReadXCleanup (
- ilReadXPrivPtr pPriv
- )
- {
- if (pPriv->copyPixmap) {
- XFreePixmap (pPriv->display, pPriv->copyPixmap);
- pPriv->copyPixmap = (Pixmap)0;
- }
- return IL_OK;
- }
- /* ------------------------ ilReadXDestroy ------------------------------- */
- /* Destroy() function for ilReadXDrawable() pipe elements.
- Free anything in private that was created when the element was added.
- */
- static ilError ilReadXDestroy (
- ilReadXPrivPtr pPriv
- )
- {
- if (pPriv->pPalette)
- IL_FREE (pPriv->pPalette);
- if (pPriv->grayMapImage)
- ilDestroyObject (pPriv->grayMapImage);
- return IL_OK;
- }
- /* ------------------------ ilReadXExecute ------------------------------- */
- /* Execute() function for ilReadXDrawable() pipe elements.
- */
- static ilError ilReadXExecute (
- ilExecuteData *pData,
- long dstLine,
- long *pNLines
- )
- {
- ilReadXPrivPtr pPriv;
- Drawable readDrawable;
- ilBool lastStrip;
- long nLines;
- int srcX, srcY;
- XImage *Ximage;
- ilPtr pSrcLine, pDstLine;
- long srcRowBytes, dstRowBytes, nBytesToCopy;
- /* Read pPriv->stripHeight lines from the drawable, but if that takes
- us off the end, read less, and note that this is lastStrip.
- */
- pPriv = (ilReadXPrivPtr)pData->pPrivate;
- if ((pData->srcLine + pPriv->stripHeight) >= pPriv->rect.height) {
- nLines = pPriv->rect.height - pData->srcLine;
- lastStrip = TRUE;
- }
- else {
- nLines = pPriv->stripHeight;
- lastStrip = FALSE;
- }
- if (nLines <= 0)
- return (lastStrip) ? IL_ERROR_LAST_STRIP : IL_OK;
- /* If "copyPixmap" non-null, blt from drawable into it at (0,0), and set src (X,Y)
- to (0,0) - always GetImage() from left-top of it. Then XGetImage() "nLines"
- from readDrawable (drawable or pixmap), and copy the bits into pDstImage's
- buffer at (0, "dstLine").
- */
- if (pPriv->copyPixmap) {
- XCopyArea (pPriv->display, pPriv->drawable, pPriv->copyPixmap, pPriv->copyGC,
- pPriv->rect.x, pPriv->rect.y + pData->srcLine, pPriv->rect.width, nLines, 0, 0);
- readDrawable = pPriv->copyPixmap;
- srcX = srcY = 0;
- }
- else {
- readDrawable = pPriv->drawable;
- srcX = pPriv->rect.x;
- srcY = pPriv->rect.y + pData->srcLine;
- }
- Ximage = XGetImage (pPriv->display, readDrawable, srcX, srcY, pPriv->rect.width,
- nLines, ~0, ZPixmap);
- if (!Ximage)
- return IL_ERROR_X_GET_IMAGE;
- /* Bump srcLine by # of lines gotten, and copy that many lines to pDstImage.
- Set nBytesToCopy to lesser of src and dstRowBytes.
- */
- *pNLines = nLines;
- pData->srcLine += nLines;
- pSrcLine = (ilPtr)Ximage->data;
- srcRowBytes = Ximage->bytes_per_line;
- dstRowBytes = pData->pDstImage->plane[0].nBytesPerRow;
- nBytesToCopy = (srcRowBytes < dstRowBytes) ? srcRowBytes : dstRowBytes;
- pDstLine = pData->pDstImage->plane[0].pPixels + dstLine * dstRowBytes;
- /* If a long/pixel image, must extract IL RGB bytes from X long/pixel image.
- */
- if (pPriv->isLongImage) {
- ilPtr pDst;
- unsigned long temp, *pSrc;
- long nLongsM1;
- while (nLines-- > 0) {
- pSrc = (unsigned long *)pSrcLine;
- pSrcLine += srcRowBytes;
- pDst = pDstLine;
- pDstLine += dstRowBytes;
- nLongsM1 = pPriv->rect.width - 1; /* width > 0, from ilReadXDrawable() */
- do {
- temp = *pSrc++; /* long = <unused,r,g,b> each 8 bits */
- *(pDst + 2) = temp; /* red */
- temp >>= 8;
- *(pDst + 1) = temp; /* green */
- temp >>= 8;
- *pDst = temp; /* blue */
- pDst += 3; /* next dst pixel */
- } while (--nLongsM1 >= 0);
- }
- }
- else {
- /* Byte or bit/pixel: if 1 bit/pixel image and LSBFirst bit order, reverse
- the bits using lookup table, else copy: if bytes/row same for X/IL images,
- copy buffer, else one line at a time.
- */
- if ((Ximage->depth == 1) && (Ximage->bitmap_bit_order == LSBFirst)) {
- ilPtr pSrc, pDst;
- long nBytesM1;
- if (nBytesToCopy > 0)
- while (nLines-- > 0) {
- pSrc = pSrcLine;
- pSrcLine += srcRowBytes;
- pDst = pDstLine;
- pDstLine += dstRowBytes;
- nBytesM1 = nBytesToCopy - 1;
- do {
- *pDst++ = ilBitReverseTable[*pSrc++];
- } while (--nBytesM1 >= 0);
- }
- }
- else {
- if (srcRowBytes == dstRowBytes)
- bcopy ((char *)pSrcLine, (char *)pDstLine, nLines * srcRowBytes);
- else {
- while (nLines-- > 0) {
- bcopy ((char *)pSrcLine, (char *)pDstLine, nBytesToCopy);
- pSrcLine += srcRowBytes;
- pDstLine += dstRowBytes;
- }
- }
- }
- }
- XDestroyImage (Ximage);
- return (lastStrip) ? IL_ERROR_LAST_STRIP : IL_OK;
- }
- /* ------------------------ ilReadXExecuteSlow ------------------------------- */
- /* Execute() function for ilReadXDrawable() pipe elements.
- */
- static ilError ilReadXExecuteSlow (
- ilExecuteData *pData,
- long dstLine,
- long *pNLines
- )
- {
- ilReadXPrivPtr pPriv;
- ilReadXPrivRec priv;
- Drawable readDrawable;
- ilBool lastStrip;
- long nLines;
- int srcX, srcY;
- XImage *Ximage;
- ilPtr pSrcLine, pDstLine;
- long srcRowBytes, dstRowBytes, nBytesToCopy;
- /* Read pPriv->stripHeight lines from the drawable, but if that takes
- us off the end, read less, and note that this is lastStrip.
- */
- pPriv = (ilReadXPrivPtr)pData->pPrivate;
- if ((pData->srcLine + pPriv->stripHeight) >= pPriv->rect.height) {
- nLines = pPriv->rect.height - pData->srcLine;
- lastStrip = TRUE;
- }
- else {
- nLines = pPriv->stripHeight;
- lastStrip = FALSE;
- }
- if (nLines <= 0)
- return (lastStrip) ? IL_ERROR_LAST_STRIP : IL_OK;
- /* If "copyPixmap" non-null, blt from drawable into it at (0,0), and set src (X,Y)
- to (0,0) - always GetImage() from left-top of it. Then XGetImage() "nLines"
- from readDrawable (drawable or pixmap), and copy the bits into pDstImage's
- buffer at (0, "dstLine").
- */
- if (pPriv->copyPixmap) {
- XCopyArea (pPriv->display, pPriv->drawable, pPriv->copyPixmap, pPriv->copyGC,
- pPriv->rect.x, pPriv->rect.y + pData->srcLine, pPriv->rect.width, nLines, 0, 0);
- readDrawable = pPriv->copyPixmap;
- srcX = srcY = 0;
- }
- else {
- readDrawable = pPriv->drawable;
- srcX = pPriv->rect.x;
- srcY = pPriv->rect.y + pData->srcLine;
- }
- Ximage = XGetImage (pPriv->display, readDrawable, srcX, srcY, pPriv->rect.width,
- nLines, ~0, ZPixmap);
- if (!Ximage)
- return IL_ERROR_X_GET_IMAGE;
- /* Bump srcLine by # of lines gotten, and copy that many lines to pDstImage.
- Set nBytesToCopy to lesser of src and dstRowBytes.
- */
- *pNLines = nLines;
- pData->srcLine += nLines;
- pSrcLine = (ilPtr)Ximage->data;
- srcRowBytes = Ximage->bytes_per_line;
- dstRowBytes = pData->pDstImage->plane[0].nBytesPerRow;
- nBytesToCopy = (srcRowBytes < dstRowBytes) ? srcRowBytes : dstRowBytes;
- pDstLine = pData->pDstImage->plane[0].pPixels + dstLine * dstRowBytes;
- /* If a long/pixel image, must extract IL RGB bytes from X long/pixel image.
- */
- if (pPriv->isLongImage) {
- ilPtr pDst;
- unsigned long temp, *pSrc;
- long nLongsM1;
- unsigned int X, Y;
- XVisualInfo *pVisualInfo;
- unsigned int pixel;
- int bit, count;
- /************* slow pixel code*****************/
-
- if (((pPriv->nRedOnes <= 8) && (pPriv->nRedOnes >= 1))
- && ((pPriv->nGreenOnes <= 8) && (pPriv->nGreenOnes >= 1))
- && ((pPriv->nBlueOnes <= 8) && (pPriv->nBlueOnes >= 1))) {
-
- for ( Y = 0; Y < nLines; Y++) {
- pDst = pDstLine;
- pDstLine += dstRowBytes;
- for ( X = 0 ; X < pPriv->rect.width; X++) {
- pixel = XGetPixel(Ximage, X, Y );
- /* Red */
- *pDst++ = (pixel & pPriv->OrgRedMask) >> pPriv->nRedZeros;
- /* Green */
- *pDst++ = (pixel & pPriv->OrgGreenMask) >> pPriv->nGreenZeros;
- /* Blue */
- *pDst++ = (pixel & pPriv->OrgBlueMask) >> pPriv->nBlueZeros;
-
- }
- }
- }
- }
-
-
- else {
- /* Byte or bit/pixel: if 1 bit/pixel image and LSBFirst bit order, reverse
- the bits using lookup table, else copy: if bytes/row same for X/IL images,
- copy buffer, else one line at a time.
- */
- if ((Ximage->depth == 1) && (Ximage->bitmap_bit_order == LSBFirst)) {
- ilPtr pSrc, pDst;
- long nBytesM1;
- if (nBytesToCopy > 0)
- while (nLines-- > 0) {
- pSrc = pSrcLine;
- pSrcLine += srcRowBytes;
- pDst = pDstLine;
- pDstLine += dstRowBytes;
- nBytesM1 = nBytesToCopy - 1;
- do {
- *pDst++ = ilBitReverseTable[*pSrc++];
- } while (--nBytesM1 >= 0);
- }
- }
- else {
- if (srcRowBytes == dstRowBytes)
- bcopy ((char *)pSrcLine, (char *)pDstLine, nLines * srcRowBytes);
- else {
- while (nLines-- > 0) {
- bcopy ((char *)pSrcLine, (char *)pDstLine, nBytesToCopy);
- pSrcLine += srcRowBytes;
- pDstLine += dstRowBytes;
- }
- }
- }
- }
- XDestroyImage (Ximage);
- return (lastStrip) ? IL_ERROR_LAST_STRIP : IL_OK;
- }
- /* ------------------------ ilReadXDrawable ---------------------------- */
- /* Public function; see spec.
- */
- ilBool ilReadXDrawable (
- ilPipe pipe,
- Display *display,
- Drawable drawable,
- Visual *visual,
- Colormap colormap,
- ilBool blackIsZero,
- ilRect *pSrcRect,
- ilBool copyToPixmap,
- unsigned long flags
- )
- {
- ilReadXPrivRec priv; /* pre-inited private block; becomes *pPriv */
- ilPipeInfo info;
- ilImageDes des;
- ilImageFormat format;
- ilError error;
- int pixelSize, notUsed;
- ilDstElementData dstData;
- XVisualInfo template, *pVisualInfo;
- ilReadXPrivPtr pPriv;
- Window root;
- int x, y;
- unsigned int border_width;
- unsigned int width, height, depth; /* values for drawable */
- Bool SlowMode = FALSE;
- unsigned int pixel;
- int bit, count, nRedZeros, nGreenZeros, nBlueZeros;
- int nRedOnes, nGreenOnes, nBlueOnes;
- int RedMask, GreenMask, BlueMask;
- /*int OrgRedMask, OrgGreenMask, OrgBlueMask;*/
- if (pipe->objectType != IL_PIPE) {
- pipe->context->error = IL_ERROR_OBJECT_TYPE;
- return FALSE;
- }
- if (flags & ~1)
- return ilDeclarePipeInvalid (pipe, IL_ERROR_PAR_NOT_ZERO);
- /* Get pipe info; if pipe not in IL_PIPE_EMPTY state: error.
- Get width, height and depth of the requested drawable.
- */
- if (ilGetPipeInfo (pipe, FALSE, &info, &des, &format) != IL_PIPE_EMPTY) {
- if (!pipe->context->error)
- ilDeclarePipeInvalid (pipe, IL_ERROR_PIPE_STATE);
- return FALSE;
- }
- if (!XGetGeometry (display, drawable, &root, &x, &y, &width, &height,
- &border_width, &depth))
- return ilDeclarePipeInvalid (pipe, IL_ERROR_X_DRAWABLE);
- /* Init priv with what we have so far. Set "priv.rect" to rectangle to read from
- drawable: bounds of drawable, intersected with pSrcRect if present.
- Null priv. objects - call ilReadXDestroy() on failure to free non-nulls.
- */
- priv.display = display;
- priv.drawable = drawable;
- priv.visual = visual;
- priv.colormap = colormap;
- priv.pPalette = (unsigned short *)NULL;
- priv.grayMapImage = (ilClientImage)NULL;
- priv.isLongImage = FALSE;
- priv.rgbMapImage = (ilClientImage)NULL;
- priv.rect.x = priv.rect.y = 0;
- priv.rect.width = width;
- priv.rect.height = height;
- if (pSrcRect)
- _ilIntersectRect (pSrcRect, &priv.rect);
- if ((priv.rect.width <= 0) || (priv.rect.height <= 0))
- return ilDeclarePipeInvalid (pipe, IL_ERROR_ZERO_SIZE_IMAGE);
- /* Do type-specific setup: set pixelSize based on des.type; set des and format.
- If no visual or colormap: if not depth 1, error; else a bitmap: handle here.
- */
- if (!visual || !colormap) {
- if (depth != 1) /* not a bitmap */
- return ilDeclarePipeInvalid (pipe, IL_ERROR_X_COLORMAP_VISUAL);
- des = *IL_DES_BITONAL;
- des.blackIsZero = blackIsZero;
- format = *IL_FORMAT_BIT;
- pixelSize = 1;
- }
- else {
- /* Not a bitmap: get info from "visual"; depths must match.
- Set "supported" true if this visual handled, else break (becomes error).
- */
- if (!colormap || !visual)
- return ilDeclarePipeInvalid (pipe, IL_ERROR_X_COLORMAP_VISUAL);
- template.visualid = XVisualIDFromVisual (visual);
- pVisualInfo = XGetVisualInfo (display, VisualIDMask, &template, ¬Used);
- if (!pVisualInfo)
- return ilDeclarePipeInvalid (pipe, IL_ERROR_X_RESOURCE);
- if (pVisualInfo->depth != depth)
- return ilDeclarePipeInvalid (pipe, IL_ERROR_UNSUPPORTED_VISUAL);
- priv.colormapSize = pVisualInfo->colormap_size;
- switch (pVisualInfo->class) {
- /* Support 1 and 8 bit gray scale. For 1 bit, query color map to
- determine blackIsZero (assume is if pixel 0 = rgb of 0,0,0.)
- For 8 bit, add an ilMap() element using pPriv->grayMapImage, which
- is setup in ilReadXInit() with the gray value for each X pixel.
- However, skip this step if rawMode.
- */
- case GrayScale:
- case StaticGray:
- if (depth == 1) {
- XColor color;
- color.pixel = 0;
- XQueryColor (display, colormap, &color);
- des = *IL_DES_BITONAL;
- des.blackIsZero = (!color.red && !color.green && !color.blue);
- format = *IL_FORMAT_BIT;
- pixelSize = 1;
- priv.SlowMode = SlowMode;
- }
- else if ((depth <= 8) && (depth > 1)) {
- ilImageInfo imageInfo, *pImageInfo;
- if (!(flags & IL_READ_X_RAW_MODE)) {
- imageInfo.pDes = IL_DES_GRAY;
- imageInfo.pFormat = IL_FORMAT_BYTE;
- imageInfo.width = 256;
- imageInfo.height = 1;
- imageInfo.clientPixels = FALSE;
- priv.grayMapImage = ilCreateClientImage (pipe->context,
- &imageInfo, 0);
- if (!priv.grayMapImage)
- return FALSE;
- ilQueryClientImage (priv.grayMapImage, &pImageInfo, 0);
- priv.pGrayMapPixels = pImageInfo->plane[0].pPixels;
- }
- des = *IL_DES_GRAY;
- format = *IL_FORMAT_BYTE;
- pixelSize = 8;
- }
-
- else return ilDeclarePipeInvalid (pipe, IL_ERROR_UNSUPPORTED_VISUAL);
- SlowMode = depth < 8;
- priv.SlowMode = SlowMode;
- break;
- /* Support 8 bit Pseudo/StaticColor as palette image; alloc palette. */
- case StaticColor:
- case PseudoColor:
- if (depth > 8)
- return ilDeclarePipeInvalid (pipe, IL_ERROR_UNSUPPORTED_VISUAL);
- des = *IL_DES_GRAY;
- des.type = IL_PALETTE;
- des.blackIsZero = FALSE;
- format = *IL_FORMAT_BYTE;
- pixelSize = 8;
- if (!(priv.pPalette = (unsigned short *)
- IL_MALLOC_ZERO (sizeof(unsigned short) * (3 * 256))))
- return ilDeclarePipeInvalid (pipe, IL_ERROR_MALLOC);
- SlowMode = depth < 8;
- priv.SlowMode = SlowMode;
-
- break;
- /* Support True/DirectColor only if format = "<unused 8><8R><8G><8B>". */
- case DirectColor:
- case TrueColor:
- if ((depth == 24)
- && (pVisualInfo->red_mask == 0xff0000)
- && (pVisualInfo->green_mask == 0xff00)
- && (pVisualInfo->blue_mask == 0xff)) {
- ilImageInfo imageInfo, *pImageInfo;
- if (!(flags & IL_READ_X_RAW_MODE)) {
- imageInfo.pDes = IL_DES_RGB;
- imageInfo.pFormat = IL_FORMAT_3BYTE_PIXEL;
- imageInfo.width = 256;
- imageInfo.height = 1;
- imageInfo.clientPixels = FALSE;
- priv.rgbMapImage = ilCreateClientImage (pipe->context,
- &imageInfo, 0);
- if (!priv.rgbMapImage)
- return FALSE;
- ilQueryClientImage (priv.rgbMapImage, &pImageInfo, 0);
- priv.pRGBMapPixels = pImageInfo->plane[0].pPixels;
- }
- des = *IL_DES_RGB;
- format = *IL_FORMAT_3BYTE_PIXEL;
- pixelSize = 24;
- priv.isLongImage = TRUE;
- priv.SlowMode = SlowMode;
- }
-
- /*suport for Gacko and 12 bit display depth */
- else {
- /*counting the number of ones and zeros in each red,
- green and blue mask */
- /* calculating Number of zeros and ones for red_mask */
- /******************************************************/
- priv.OrgRedMask = pVisualInfo->red_mask;
- RedMask = pVisualInfo->red_mask;
- bit = 1;
- nRedOnes = 0;
- while(bit<0xffffff) {
- if (RedMask & bit) nRedOnes++;
- bit <<= 1;
- }
-
- /* nRedZeros = 8 - nRedOnes;
- priv.nRedZeros = nRedZeros; */
- priv.nRedOnes = nRedOnes;
- bit = 1;
- count = 0;
- while(!(RedMask & bit)){
- count++;
- RedMask >>= 1;
- }
- nRedZeros = count;
- priv.nRedZeros = nRedZeros;
-
- /* calculating Number of zeros and ones for Green_mask */
- /*******************************************************/
- priv.OrgGreenMask = pVisualInfo->green_mask;
- GreenMask = pVisualInfo->green_mask;
- bit = 1;
- nGreenOnes = 0;
- while(bit<0xffffff) {
- if (GreenMask & bit) nGreenOnes++;
- bit <<= 1;
- }
- /* nGreenZeros = 8 - nGreenOnes;
- priv.nGreenZeros = nGreenZeros; */
- priv.nGreenOnes = nGreenOnes;
- bit = 1;
- count = 0;
- while(!(GreenMask & bit )){
- count++;
- GreenMask >>= 1;
- }
- nGreenZeros = count;
- priv.nGreenZeros = nGreenZeros;
- /* calculating Number of zeros and ones for blue_mask */
- /******************************************************/
- priv.OrgBlueMask = pVisualInfo->blue_mask;
- BlueMask = pVisualInfo->blue_mask;
- bit = 1;
- nBlueOnes = 0;
- while(bit<0xffffff) {
- if (BlueMask & bit) nBlueOnes++;
- bit <<= 1;
- }
- /* nBlueZeros = 8 - nBlueOnes;
- priv.nBlueZeros = nBlueZeros; */
- priv.nBlueOnes = nBlueOnes;
- bit = 1;
- count = 0;
- while(!(BlueMask & bit)){
- count++;
- BlueMask >>= 1;
- }
- nBlueZeros = count;
- priv.nBlueZeros = nBlueZeros;
- if ((depth <=32)
- &&((nRedOnes <= 8) && (nRedOnes >= 1))
- &&((nGreenOnes <= 8) && (nGreenOnes >= 1))
- &&((nBlueOnes <= 8) && (nBlueOnes >= 1))) {
-
- ilImageInfo imageInfo, *pImageInfo;
- if (!(flags & IL_READ_X_RAW_MODE)) {
- imageInfo.pDes = IL_DES_RGB;
- imageInfo.pFormat = IL_FORMAT_3BYTE_PIXEL;
- imageInfo.width = 256;
- imageInfo.height = 1;
- imageInfo.clientPixels = FALSE;
- priv.rgbMapImage = ilCreateClientImage (pipe->context,
- &imageInfo, 0);
- if (!priv.rgbMapImage)
- return FALSE;
- ilQueryClientImage (priv.rgbMapImage, &pImageInfo, 0);
- priv.pRGBMapPixels = pImageInfo->plane[0].pPixels;
- }
- des = *IL_DES_RGB;
- format = *IL_FORMAT_3BYTE_PIXEL;
- pixelSize = 24;
- priv.isLongImage = TRUE;
- SlowMode = depth<= 32;
- priv.SlowMode = SlowMode;
- }
-
- else return ilDeclarePipeInvalid (pipe, IL_ERROR_UNSUPPORTED_VISUAL);
- }
- /* SlowMode = depth<= 32;
- pPriv.SlowMode = SlowMode;*/
- break;
- } /* END switch visual class */
- } /* END not a bitmap */
-
- /* Visual (or a bitmap) supported; read in strips to conserve memory. */
- priv.stripHeight = ilRecommendedStripHeight (&des, &format, priv.rect.width,
- priv.rect.height);
- /* Create a GC if copyToPixmap (set copyPixmapDepth != 0). Null ptrs
- out and call ilReadXDestroy() if failure - it will free non-null objects.
- */
- priv.copyPixmap = (Pixmap)0;
- priv.copyPixmapDepth = 0;
- priv.copyGC = (GC)NULL;
- if (copyToPixmap) {
- XGCValues values;
- values.subwindow_mode = IncludeInferiors; /* get subwindow contents */
- priv.copyGC = XCreateGC (priv.display, priv.drawable, GCSubwindowMode, &values);
- if (!priv.copyGC) {
- ilReadXDestroy (&priv);
- return ilDeclarePipeInvalid (pipe, IL_ERROR_X_RESOURCE);
- }
- priv.copyPixmapDepth = depth;
- }
- /* Add a producer element to read from the X drawable; copy priv into *pPriv. */
- dstData.producerObject = (ilObject)NULL;
- dstData.pDes = &des;
- dstData.pFormat = &format;
- dstData.width = priv.rect.width;
- dstData.height = priv.rect.height;
- dstData.stripHeight = priv.stripHeight;
- dstData.constantStrip = TRUE;
- dstData.pPalette = priv.pPalette;
-
-
- pPriv = (ilReadXPrivPtr)ilAddPipeElement (pipe, IL_PRODUCER, sizeof (ilReadXPrivRec),
- 0, (ilSrcElementData *)NULL, &dstData, ilReadXInit, ilReadXCleanup,
- ilReadXDestroy, ((SlowMode)?ilReadXExecuteSlow:ilReadXExecute), 0);
-
-
- /*
- pPriv = (ilReadXPrivPtr)ilAddPipeElement (pipe, IL_PRODUCER, sizeof (ilReadXPrivRec),
- 0, (ilSrcElementData *)NULL, &dstData, ilReadXInit, ilReadXCleanup,
- ilReadXDestroy, ilReadXExecuteSlow, 0);
-
- */
-
- if (!pPriv) {
- ilReadXDestroy (&priv);
- return FALSE;
- }
- *pPriv = priv;
- /* If a gray/rgbMapImage, use ilMap() to remap from colormap values. */
- if (priv.grayMapImage)
- return ilMap (pipe, priv.grayMapImage);
- else if (priv.rgbMapImage)
- return ilMap (pipe, priv.rgbMapImage);
- pipe->context->error = IL_OK;
- return TRUE;
- }
|