📄 dev2gif.c
字号:
XImg = XGetImage((Display *) ReqGraphMode2, (Window) ReqGraphMode1, 0, 0, ScreenXMax - 1, ScreenYMax - 1, AllPlanes, XYPixmap); GlblGifBuffer = (GifByteType *)malloc(sizeof(GifByteType) * ScreenXMax * ScreenYMax); /* Scan the image for all different colors exists. */ for (i = 0; i < 256; i++) XColorTable[i].pixel = 0; k = FALSE; for (i = 0; i < ScreenXMax; i++) for (j = 0; j < ScreenYMax; j++) { XPixel = XGetPixel(XImg, i, j); if (XPixel > 255) { if (!k) { /* Make sure we state it once only. */ fprintf(stderr, "X Color table - truncated.\n"); k = TRUE; } XPixel = 255; } XColorTable[XPixel].pixel = XPixel; } /* Find the RGB representation of the colors. */ XQueryColors((Display *) ReqGraphMode2, (Colormap) ReqGraphMode3, XColorTable, 256); /* Count number of active colors (Note color 0 is always in) */ /* and create the Gif color map from it. */ ColorMap = MakeMapObject(256, ColorMap256); ColorMap->Colors[0].Red = ColorMap->Colors[0].Green = ColorMap->Colors[0].Blue = 0; for (i = j = 1; i < 256; i++) if (XColorTable[i].pixel) { ColorMap->Colors[j].Red = XColorTable[i].red / 256; ColorMap->Colors[j].Green = XColorTable[i].green / 256; ColorMap->Colors[j].Blue = XColorTable[i].blue / 256; /* Save the X color index into the Gif table: */ XColorTable[i].pixel = j++; } /* and set the number of colors in the Gif color map. */ for (ScreenColorBits = 1; (1 << ScreenColorBits) < j && ScreenColorBits < 8; ScreenColorBits++) ; /* Prepare the Gif image buffer as indices into the Gif color */ /* map from the X image. */ GlblGifBufferPtr = GlblGifBuffer; for (i = 0; i < ScreenXMax; i++) for (j = 0; j < ScreenYMax; j++) *GlblGifBufferPtr++ = XColorTable[XGetPixel(XImg, j, i) & 0xff].pixel; XDestroyImage(XImg); GlblGifBufferPtr = GlblGifBuffer; ColorMap = MakeMapObject(256, ColorMap256); break;#endif /* HAVE_LIBX11 */ default: return -1; } ScanLine = (GifPixelType *)malloc(sizeof(GifPixelType) * ScreenXMax); GraphDriver = ReqGraphDriver; GraphMode = ReqGraphMode1; if ((GifFile = EGifOpenFileName(FileName, FALSE)) == NULL || EGifPutScreenDesc(GifFile, ScreenXMax, ScreenYMax, ScreenColorBits, 0, ColorMap) == GIF_ERROR || EGifPutImageDesc(GifFile, 0, 0, ScreenXMax, ScreenYMax, FALSE, NULL) == GIF_ERROR) { free((char *)ScanLine);#if defined(HAVE_LIBGL_S) || defined(HAVE_LIBX11) free((char *)GlblGifBuffer);#endif return HandleGifError(GifFile); } for (i = 0; i < ScreenYMax; i++) { GetScanLine(ScanLine, i); if (EGifPutLine(GifFile, ScanLine, ScreenXMax) == GIF_ERROR) { free((char *)ScanLine);#if defined(HAVE_LIBGL_S) || defined(HAVE_LIBX11) free((char *)GlblGifBuffer);#endif return HandleGifError(GifFile); } } if (EGifCloseFile(GifFile) == GIF_ERROR) { free((char *)ScanLine);#if defined(HAVE_LIBGL_S) || defined(HAVE_LIBX11) free((char *)GlblGifBuffer);#endif return HandleGifError(GifFile); } free((char *)ScanLine);#if defined(HAVE_LIBGL_S) || defined(HAVE_LIBX11) free((char *)GlblGifBuffer);#endif return 0;}#ifdef HAVE_LIBGL_S/****************************************************************************** * Quantize the given 24 bit (8 per RGB) into 256 colors. *****************************************************************************/static intQuantizeRGBBuffer(int Width, int Height, long *RGBBuffer, GifColorType * ColorMap, GifByteType * GIFBuffer) { int i; GifByteType *RedInput, *GreenInput, *BlueInput; /* Convert the RGB Buffer into 3 seperated buffers: */ RedInput = (GifByteType *) malloc(sizeof(GifByteType) * Width * Height); GreenInput = (GifByteType *) malloc(sizeof(GifByteType) * Width * Height); BlueInput = (GifByteType *) malloc(sizeof(GifByteType) * Width * Height); for (i = 0; i < Width * Height; i++) { RedInput[i] = RGBBuffer[i] & 0xff; GreenInput[i] = (RGBBuffer[i] >> 8) & 0xff; BlueInput[i] = (RGBBuffer[i] >> 16) & 0xff; } for (i = 0; i < 256; i++) ColorMap[i].Red = ColorMap[i].Green = ColorMap[i].Blue = 0; i = 256; QuantizeBuffer(Width, Height, &i, RedInput, GreenInput, BlueInput, GIFBuffer, ColorMap); free(RedInput); free(GreenInput); free(BlueInput); return i; /* Real number of colors in color table. */}#endif /* HAVE_LIBGL_S *//****************************************************************************** * Update the given scan line buffer with the pixel levels of the Y line. * This routine is device specific, so make sure you know was you are doing *****************************************************************************/static voidGetScanLine(GifPixelType * ScanLine, int Y) { #ifdef __MSDOS__ unsigned char ScreenByte; int i, j, k; unsigned int BufferOffset, Bit; union REGS InRegs, OutRegs;#endif /* __MSDOS__ */ switch (GraphDriver) {#ifdef __MSDOS__ case HERCMONO: BufferOffset = 0x2000 * (Y % 4) + (Y / 4) * (ScreenXMax / 8); /* In one scan lines we have ScreenXMax / 8 bytes: */ for (i = 0, k = 0; i < ScreenXMax / 8; i++) { ScreenByte = (unsigned char)peekb(ScreenBase, BufferOffset++); for (j = 0, Bit = 0x80; j < 8; j++) { ScanLine[k++] = (ScreenByte & Bit ? 1 : 0); Bit >>= 1; } } break; case EGA: case EGA64: case EGAMONO: case VGA: case SVGA_SPECIAL: InRegs.x.dx = Y; InRegs.h.bh = 0; InRegs.h.ah = 0x0d; /* BIOS Read dot. */ for (i = 0; i < ScreenXMax; i++) { InRegs.x.cx = i; int86(0x10, &InRegs, &OutRegs); ScanLine[i] = OutRegs.h.al; } /* Makr this line as done by putting a xored dot on the left. */ InRegs.x.dx = Y; InRegs.h.bh = 0; InRegs.h.ah = 0x0c; /* BIOS Write dot (xor mode). */ InRegs.h.al = 0x81; /* Xor with color 1. */ InRegs.x.cx = 0; int86(0x10, &InRegs, &OutRegs); InRegs.x.dx = Y; InRegs.h.bh = 0; InRegs.h.ah = 0x0c; /* BIOS Write dot (xor mode). */ InRegs.h.al = 0x81; /* Xor with color 1. */ InRegs.x.cx = 1; int86(0x10, &InRegs, &OutRegs); if (Y == ScreenYMax - 1) { /* Last row - clear all marks we * made. */ for (i = 0; i < ScreenYMax; i++) { InRegs.h.bh = 0; InRegs.h.ah = 0x0c; /* BIOS Write dot (xor mode). */ InRegs.h.al = 0x81; /* Xor back with color 1. */ InRegs.x.dx = i; InRegs.x.cx = 0; int86(0x10, &InRegs, &OutRegs); InRegs.h.bh = 0; InRegs.h.ah = 0x0c; /* BIOS Write dot (xor mode). */ InRegs.h.al = 0x81; /* Xor back with color 1. */ InRegs.x.dx = i; InRegs.x.cx = 1; int86(0x10, &InRegs, &OutRegs); } } break;#endif /* __MSDOS__ */#ifdef HAVE_LIBGL_S case GIF_DUMP_SGI_WINDOW: memcpy(ScanLine, GlblGifBufferPtr, ScreenXMax * sizeof(GifPixelType)); GlblGifBufferPtr -= ScreenXMax; break;#endif /* HAVE_LIBGL_S */#ifdef HAVE_LIBX11 case GIF_DUMP_X_WINDOW: memcpy(ScanLine, GlblGifBufferPtr, ScreenXMax * sizeof(GifPixelType)); GlblGifBufferPtr += ScreenXMax; break;#endif /* HAVE_LIBX11 */ default: break; }}/****************************************************************************** * Handle last GIF error. Try to close the file and free all allocated memory. *****************************************************************************/static intHandleGifError(GifFileType * GifFile) { int i = GifLastError(); if (EGifCloseFile(GifFile) == GIF_ERROR) { GifLastError(); } return i;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -