home *** CD-ROM | disk | FTP | other *** search
- /*
- * xvpm.c - load routine for 'pm' format pictures
- *
- * LoadPM(fname, numcols) - loads a PM pic, does 24to8 code if nec.
- * WritePM(fp, pic, w, h, r,g,b, numcols, style)
- * WriteRaw(fp, pic, w, h, r,g,b, numcols, style)
- */
-
- /*
- * Copyright 1989, 1990, 1991, 1992 by John Bradley and
- * The University of Pennsylvania
- *
- * Permission to use, copy, and distribute for non-commercial purposes,
- * is hereby granted without fee, providing that the above copyright
- * notice appear in all copies and that both the copyright notice and this
- * permission notice appear in supporting documentation.
- *
- * The software may be modified for your own purposes, but modified versions
- * may not be distributed.
- *
- * This software is provided "as is" without any expressed or implied warranty.
- *
- * The author may be contacted via:
- * US Mail: John Bradley
- * GRASP Lab, Room 301C
- * 3401 Walnut St.
- * Philadelphia, PA 19104
- *
- * Phone: (215) 898-8813
- * EMail: bradley@cis.upenn.edu
- */
-
-
- #include "xvimage.h"
- #include "xvpm.h"
-
- pmpic thePic;
-
- static int PMError();
- static void flipl();
-
-
- /*******************************************/
- int LoadPM(fname,nc)
- char *fname;
- int nc;
- /*******************************************/
- {
- FILE *fp;
- int isize,i,flipit,w,h,rv;
-
- rv = 0;
- thePic.pm_image = NULL;
-
- /* read in the PM picture */
- fp=fopen(fname,"r");
- if (!fp) return( PMError("unable to open file") );
-
- flipit = 0;
- fread(&thePic,PM_IOHDR_SIZE,1,fp);
- if (thePic.pm_id != PM_MAGICNO) {
- flipl( (byte *) &thePic.pm_id);
- if (thePic.pm_id == PM_MAGICNO) flipit = 1;
- else flipl( (byte *) &thePic.pm_id);
- }
- if (thePic.pm_id != PM_MAGICNO) return( PMError("not a PM file") );
-
- if (flipit) {
- flipl((byte *) &thePic.pm_np); flipl((byte *) &thePic.pm_nrow);
- flipl((byte *) &thePic.pm_ncol); flipl((byte *) &thePic.pm_nband);
- flipl((byte *) &thePic.pm_form); flipl((byte *) &thePic.pm_cmtsize);
- }
-
- /* make sure that the input picture can be dealt with */
- if ( thePic.pm_nband!=1 ||
- (thePic.pm_form!=PM_I && thePic.pm_form!=PM_C) ||
- (thePic.pm_form==PM_I && thePic.pm_np>1) ||
- (thePic.pm_form==PM_C && (thePic.pm_np==2 || thePic.pm_np>4)) ) {
- fprintf(stderr,"PM picture not in a displayable format.\n");
- fprintf(stderr,"(ie, 1-plane PM_I, or 1-, 3-, or 4-plane PM_C)\n");
- return 1;
- }
-
- w = thePic.pm_ncol; h = thePic.pm_nrow;
-
- isize = pm_isize(&thePic);
-
- if (DEBUG)
- fprintf(stderr,"%s: LoadPM() - loading a %dx%d %s pic, %d planes\n",
- cmd, w, h, (thePic.pm_form==PM_I) ? "PM_I" : "PM_C",
- thePic.pm_np);
-
- sprintf(formatStr, "PM, %s. (%d plane %s) (%d bytes)",
- (thePic.pm_form==PM_I || thePic.pm_np>1) ?
- "24-bit color" : "8-bit greyscale",
- thePic.pm_np, (thePic.pm_form==PM_I) ? "PM_I" : "PM_C",
- isize + PM_IOHDR_SIZE + thePic.pm_cmtsize);
-
- /* allocate memory for picture and read it in */
- thePic.pm_image = (char *) malloc(isize);
- if (thePic.pm_image == NULL)
- return( PMError("unable to malloc PM picture") );
-
- if (fread(thePic.pm_image, (unsigned) isize, 1, fp) != 1)
- return( PMError("file read error") );
- if (fp!=stdin) fclose(fp);
-
- if (DEBUG) fprintf(stderr,"loadpm 1\n");
-
- /* convert PM picture to 'pic' (8 bit) format */
- if (thePic.pm_form == PM_I) {
- int *intptr;
- byte *pic24, *picptr;
-
- if ((pic24 = (byte *) malloc(w*h*3))==NULL)
- return( PMError("unable to malloc 24-bit picture") );
-
- intptr = (int *) thePic.pm_image;
- picptr = pic24;
-
- if (flipit) { /* if flipit, integer is RRGGBBAA instead of AABBGGRR */
- for (i=w*h; i>0; i--, intptr++) {
- *picptr++ = (*intptr>>24) & 0xff;
- *picptr++ = (*intptr>>16) & 0xff;
- *picptr++ = (*intptr>>8) & 0xff;
- }
- }
- else {
- for (i=w*h; i>0; i--, intptr++) {
- *picptr++ = (*intptr) & 0xff;
- *picptr++ = (*intptr>>8) & 0xff;
- *picptr++ = (*intptr>>16) & 0xff;
- }
- }
-
- if (DEBUG) fprintf(stderr,"loadpm 2\n");
-
- free(thePic.pm_image);
- rv=Conv24to8(pic24,w,h,nc);
- free(pic24);
- }
-
-
- else if (thePic.pm_form == PM_C && thePic.pm_np>1) {
- byte *pic24, *picptr, *rptr, *gptr, *bptr;
-
- if ((pic24 = (byte *) malloc(w*h*3))==NULL)
- return( PMError("unable to malloc 24-bit picture") );
-
- rptr = (byte *) thePic.pm_image;
- gptr = rptr + w*h;
- bptr = rptr + w*h*2;
- picptr = pic24;
- for (i=w*h; i>0; i--) {
- *picptr++ = *rptr++;
- *picptr++ = *gptr++;
- *picptr++ = *bptr++;
- }
- free(thePic.pm_image);
- rv=Conv24to8(pic24,w,h,nc);
- free(pic24);
- }
-
- else if (thePic.pm_form == PM_C && thePic.pm_np==1) {
- /* don't have to convert, just point pic at thePic.pm_image */
- pic = (byte *) thePic.pm_image;
- pWIDE = w; pHIGH = h;
- for (i=0; i<256; i++) r[i]=g[i]=b[i]=i; /* and build mono colortable */
- rv = 0;
- }
-
- return rv;
- }
-
-
- /*******************************************/
- int WritePM(fp, pic, w, h, rmap, gmap, bmap, numcols, colorstyle)
- FILE *fp;
- byte *pic;
- int w,h;
- byte *rmap, *gmap, *bmap;
- int numcols, colorstyle;
- {
- /* writes a PM file to the already open stream
- 'colorstyle' single-handedly determines the type of PM pic written
- if colorstyle==0, (Full Color) a 3-plane PM_C pic is written
- if colorstyle==1, (Greyscal) a 1-plane PM_C pic is written
- if colorstyle==0, (B/W stipple) a 1-plane PM_C pic is written */
-
- char foo[256];
- int i;
- byte *p;
-
- /* create 'comment' field */
- sprintf(foo,"created by 'xv %s'\n", namelist[curname]);
-
- /* fill in fields of a pmheader */
- thePic.pm_id = PM_MAGICNO;
- thePic.pm_np = (colorstyle==0) ? 3 : 1;
- thePic.pm_ncol = w;
- thePic.pm_nrow = h;
- thePic.pm_nband = 1;
- thePic.pm_form = PM_C;
- thePic.pm_cmtsize = strlen(foo);
-
- if (fwrite(&thePic, PM_IOHDR_SIZE, 1, fp) != 1) return -1;
-
- /* write the picture data */
- if (colorstyle == 0) { /* 24bit RGB, organized as 3 8bit planes */
- for (i=0,p=pic; i<w*h; i++, p++) {
- putc(rmap[*p], fp);
- }
-
- for (i=0,p=pic; i<w*h; i++, p++) {
- putc(gmap[*p], fp);
- }
-
- for (i=0,p=pic; i<w*h; i++, p++) {
- putc(bmap[*p], fp);
- }
- }
-
- else if (colorstyle == 1) { /* GreyScale: 8 bits per pixel */
- byte rgb[256];
- for (i=0; i<numcols; i++) rgb[i] = MONO(rmap[i],gmap[i],bmap[i]);
- for (i=0, p=pic; i<w*h; i++, p++) {
- putc(rgb[*p],fp);
- }
- }
-
- else /* (colorstyle == 2) */ { /* B/W stipple. pic is 1's and 0's */
- for (i=0, p=pic; i<w*h; i++, p++) {
- putc(*p ? 255 : 0,fp);
- }
- }
-
- if (fputs(foo,fp)==EOF) return -1;
-
- return 0;
- }
-
-
- /*****************************/
- static int PMError(st)
- char *st;
- {
- printf("LoadPM() - %s\n",cmd,st);
- if (thePic.pm_image != NULL) free(thePic.pm_image);
- return -1;
- }
-
-
- /*****************************/
- static void flipl(p)
- byte *p;
- {
- byte t;
- t = p[0]; p[0]=p[3]; p[3] = t;
- t = p[1]; p[1]=p[2]; p[2] = t;
- }
-
-
-
-
-
-
-
-
-
-
-
-
-