This is bmpimage.c in view mode; [Download] [Up]
#include <stdio.h> #include <libc.h> #include "bmp.h" static xdelta, ydelta, compmode; static int bmpGetPalette(FILE *fp, bmpHeader *bh) /* ¥Ñ¥ì¥Ã¥È¤òÆɤ߹þ¤ó¤Ç¤½¤ÎÎΰè¤ÎÀèƬ¥¢¥É¥ì¥¹¤ò bh->palette¤ËÂåÆþ¡£ ¥¨¥é¡¼¤Î»þ¡¢¤ª¤è¤Ó24¥Ó¥Ã¥È¥«¥é¡¼¤Î»þ¤Ë¤Ï NULL ¤¬Æþ¤ë¡£ ÊÖ¤êÃͤϡ¢À®¸ù¤Î¾ì¹ç 0, ¥¨¥é¡¼¤Î¾ì¹ç¤Ï¸¶°ø(!=0)¡£ */ { int i, color; paltype *pal = NULL; unsigned char *p; bh->palette = NULL; if (bh->bits == 24) /* 24¥Ó¥Ã¥È¥«¥é¡¼¤Ï¥Ñ¥ì¥Ã¥ÈÉÔÍ× */ return 0; color = 1 << bh->bits; pal = (paltype *)malloc(sizeof(paltype) * color); if (bh->type == OS2) { for (i = 0; i < color; i++) { p = pal[i]; p[BLUE] = getc(fp); p[GREEN] = getc(fp); p[RED] = getc(fp); } }else { /* WIN3 */ for (i = 0; i < color; i++) { p = pal[i]; p[BLUE] = getc(fp); p[GREEN] = getc(fp); p[RED] = getc(fp); (void) getc(fp); } } bh->palette = pal; if (feof(fp) || fseek(fp, bh->bitoffset, SEEK_SET) < 0) return Err_SHORT; return 0; } static int get1dot(FILE *fp, int wid, unsigned char *ln) { int x, cnt, cc, mask; if (feof(fp)) return -1; for (x = 0, cnt = 0; x < wid; cnt++) { cc = getc(fp); for (mask = 0x80; mask; mask >>= 1) ln[x++] = (cc & mask) ? 1 : 0; } for ( ; cnt & 0x03; cnt++) (void) getc(fp); return 0; } static int get4dots(FILE *fp, int wid, unsigned char *ln) { int x, cnt, cc; if (feof(fp)) return -1; for (x = 0, cnt = 0; x < wid; cnt++) { cc = getc(fp); ln[x++] = cc >> 4; ln[x++] = (cc & 0x0f); } for ( ; cnt & 0x03; cnt++) (void) getc(fp); return 0; } static int get8dots(FILE *fp, int wid, unsigned char *ln) { int cnt; if (feof(fp)) return -1; for (cnt = 0; cnt < wid; cnt++) ln[cnt] = getc(fp); for ( ; cnt & 0x03; cnt++) (void) getc(fp); return 0; } static int rledots(FILE *fp, int wid, unsigned char *ln) { int i, j, k, cc, count; int half[2]; if (feof(fp)) return -1; for (i = 0; i < wid; i++) ln[i] = 0; if (ydelta > 0) { ydelta--; return 0; } count = wid; if (xdelta > 0) { if (xdelta > count) { xdelta = 0; return 0; } count -= xdelta; ln += xdelta; } xdelta = 0; for ( ; ; ) { i = getc(fp); if (i) { /* Codec Mode */ if (i > count) i = count; count -= i; cc = getc(fp); if (compmode == RLE8) { while (i-- > 0) *ln++ = cc; }else { half[0] = cc >> 4; half[1] = cc & 0x0f; for (k = 0; i-- > 0; k ^= 1) *ln++ = half[k]; } continue; } /* Absolute Mode */ j = getc(fp); if (j == 0 || j == 1) /* EOL / EOF */ break; /* return */ if (j == 2) { /* Delta Mode */ xdelta = getc(fp); /* X-offset */ ydelta = getc(fp); /* Y-offset */ if (ydelta == 0) { count -= xdelta; ln += xdelta; xdelta = 0; }else { xdelta += wid - count; ydelta--; break; /* return */ } }else { if (j > count) j = count; count -= j; if (compmode == RLE8) { k = j & 1; /* 16-bit packing */ while (j-- > 0) *ln++ = getc(fp); }else { k = (j + 1) & 2; /* 16-bit packing */ while (j-- > 0) { cc = getc(fp); *ln++ = cc >> 4; if (j-- <= 0) break; *ln++ = cc & 0x0f; } } if (k) (void) getc(fp); } } return 0; } int bmpGetImage(FILE *fp, bmpHeader *bh, int *bits, unsigned char **planes) /* ¥Õ¥¡¥¤¥ë¤«¤é¥¤¥á¡¼¥¸¥Ç¡¼¥¿¤òÆɤ߽Ф·¡¢R,G,B ¤Î£³¤Ä¤Î¥×¥ì¡¼¥ó¤ÎÀèƬ ¥¢¥É¥ì¥¹¤ò planes[0]~[2] ¤Ë¥»¥Ã¥È¤¹¤ë¡£³Æ¿§¤ËɬÍפʥԥ¯¥»¥ë¿ô¤Ï bits ¤ËÆþ¤ì¤é¤ì¤ë¡£mh¤Ë¤Ï¥Ø¥Ã¥À¾öÊó¤ò»ØÄꤹ¤ë¡£ */ { int x, wid, y, w; int colbit = 8, colnum = 0; int err = 0; BOOL isgray = NO; int (*getNdots)(FILE *, int, unsigned char *) = get8dots; if (bh->comp) { if (bh->comp == RLE8) colnum = 256; else if (bh->comp == RLE4) colnum = 16; else return Err_IMPLEMENT; compmode = bh->comp; getNdots = rledots; }else { compmode = NoComp; if (bh->bits == 1) getNdots = get1dot; else if (bh->bits == 4) getNdots = get4dots; else if (bh->bits == 8) getNdots = get8dots; colnum = 1 << bh->bits; } /* else bits == 24 */ if ((err = bmpGetPalette(fp, bh)) != 0) return err; if (colnum && bh->bits < 24) { colbit = howManyBits(bh->palette, colnum); isgray = isGray(bh->palette, colnum); } wid = byte_length(colbit, bh->x); err = allocImage(planes, bh->x, bh->y, colbit, (isgray ? 1 : 3)); if (err) return err; if (bh->bits <= 8) { unsigned char line[MAXWidth]; unsigned char *map[MAXPLANE]; *bits = colbit; for (y = bh->y - 1; y >= 0; y--) { if (getNdots(fp, bh->x, line) < 0) return Err_SHORT; map[0] = planes[0] + (w = wid * y); map[1] = planes[1] + w; map[2] = planes[2] + w; expandImage(map, line, (const paltype *)bh->palette, colbit, bh->x, isgray, -1); } }else { unsigned char *rr, *gg, *bb; *bits = 8; for (y = bh->y - 1; y >= 0; y--) { if (feof(fp)) return Err_SHORT; rr = planes[0] + (w = wid * y); gg = planes[1] + w; bb = planes[2] + w; for (x = 0; x < wid; x++) { *bb++ = getc(fp); *gg++ = getc(fp); *rr++ = getc(fp); } for (x *= 3 ; x & 0x03; x++) (void) getc(fp); } } return 0; }
These are the contents of the former NiCE NeXT User Group NeXTSTEP/OpenStep software archive, currently hosted by Netfuture.ch.