ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/px/x11image.c
(Generate patch)

Comparing ray/src/px/x11image.c (file contents):
Revision 1.19 by greg, Fri May 3 09:54:31 1991 UTC vs.
Revision 2.13 by greg, Mon Oct 12 12:59:22 1992 UTC

# Line 1 | Line 1
1 < /* Copyright (c) 1990 Regents of the University of California */
1 > /* Copyright (c) 1992 Regents of the University of California */
2  
3   #ifndef lint
4   static char SCCSid[] = "$SunId$ LBL";
# Line 27 | Line 27 | static char SCCSid[] = "$SunId$ LBL";
27  
28   #include  "color.h"
29   #include  "view.h"
30 #include  "pic.h"
30   #include  "x11raster.h"
31   #include  "random.h"
32 + #include  "resolu.h"
33  
34   #define  FONTNAME       "8x13"          /* text font we'll use */
35  
36 < #define  CTRL(c)        ('c'-'@')
36 > #define  CTRL(c)        ((c)-'@')
37  
38   #define  BORWIDTH       5               /* border width */
39  
40   #define  ICONSIZ        (8*10)          /* maximum icon dimension (even 8) */
41  
42   #define  ourscreen      DefaultScreen(thedisplay)
43 #define  ourblack       BlackPixel(thedisplay,ourscreen)
44 #define  ourwhite       WhitePixel(thedisplay,ourscreen)
43   #define  ourroot        RootWindow(thedisplay,ourscreen)
46 #define  ourgc          DefaultGC(thedisplay,ourscreen)
44  
45   #define  revline(x0,y0,x1,y1)   XDrawLine(thedisplay,wind,revgc,x0,y0,x1,y1)
46  
# Line 54 | Line 51 | double  gamcor = 2.2;                  /* gamma correction */
51   int  dither = 1;                        /* dither colors? */
52   int  fast = 0;                          /* keep picture in Pixmap? */
53  
54 + char    *dispname = NULL;               /* our display name */
55 +
56   Window  wind = 0;                       /* our output window */
57 + unsigned long  ourblack=0, ourwhite=1;  /* black and white for this visual */
58   Font  fontid;                           /* our font */
59  
60   int  maxcolors = 0;                     /* maximum colors */
# Line 70 | Line 70 | int  gotview = 0;                      /* got parameters from file */
70  
71   COLR  *scanline;                        /* scan line buffer */
72  
73 < int  xmax, ymax;                        /* picture resolution */
73 > RESOLU  inpres;                         /* input resolution and ordering */
74 > int  xmax, ymax;                        /* picture dimensions */
75   int  width, height;                     /* window size */
76   char  *fname = NULL;                    /* input file name */
77   FILE  *fin = stdin;                     /* input file */
# Line 81 | Line 82 | double  exposure = 1.0;                        /* exposure compensation use
82  
83   int  wrongformat = 0;                   /* input in another format? */
84  
85 + GC      ourgc;                          /* standard graphics context */
86   GC      revgc;                          /* graphics context with GXinvert */
87  
88 < XRASTER *ourras;                        /* our stored image */
88 > int             *ourrank;               /* our visual class ranking */
89 > XVisualInfo     ourvis;                 /* our visual */
90 > XRASTER         *ourras;                /* our stored image */
91   unsigned char   *ourdata;               /* our image data */
92  
93   struct {
# Line 99 | Line 103 | char  *progname;
103  
104   char  errmsg[128];
105  
106 + extern BYTE  clrtab[256][3];            /* global color map */
107 +
108   extern long  ftell();
109  
110   extern char  *malloc(), *calloc();
111  
112 < extern double  atof(), pow(), log();
112 > extern double  pow(), log();
113  
114   Display  *thedisplay;
115  
# Line 111 | Line 117 | main(argc, argv)
117   int  argc;
118   char  *argv[];
119   {
120 +        extern char  *getenv();
121 +        char  *gv;
122          int  headline();
123          int  i;
124          
125          progname = argv[0];
126 +        if ((gv = getenv("GAMMA")) != NULL)
127 +                gamcor = atof(gv);
128  
129          for (i = 1; i < argc; i++)
130                  if (argv[i][0] == '-')
# Line 129 | Line 139 | char  *argv[];
139                                  maxcolors = 2;
140                                  break;
141                          case 'd':
142 <                                dither = !dither;
142 >                                if (argv[i][2] == 'i')
143 >                                        dispname = argv[++i];
144 >                                else
145 >                                        dither = !dither;
146                                  break;
147                          case 'f':
148                                  fast = !fast;
# Line 140 | Line 153 | char  *argv[];
153                                  scale = atoi(argv[++i]);
154                                  break;
155                          case 'g':
156 <                                if (!strcmp(argv[i], "-geometry"))
156 >                                if (argv[i][2] == 'e')
157                                          geometry = argv[++i];
158                                  else
159                                          gamcor = atof(argv[++i]);
# Line 157 | Line 170 | char  *argv[];
170                  fname = argv[i];
171                  fin = fopen(fname, "r");
172                  if (fin == NULL) {
173 <                        sprintf(errmsg, "can't open file \"%s\"", fname);
173 >                        sprintf(errmsg, "cannot open file \"%s\"", fname);
174                          quiterr(errmsg);
175                  }
176          } else if (i != argc)
# Line 165 | Line 178 | char  *argv[];
178                                  /* get header */
179          getheader(fin, headline, NULL);
180                                  /* get picture dimensions */
181 <        if (wrongformat || fgetresolu(&xmax, &ymax, fin) != (YMAJOR|YDECR))
181 >        if (wrongformat || !fgetsresolu(&inpres, fin))
182                  quiterr("bad picture format");
183 +        xmax = scanlen(&inpres);
184 +        ymax = numscans(&inpres);
185                                  /* set view parameters */
186          if (gotview && setview(&ourview) != NULL)
187                  gotview = 0;
# Line 179 | Line 194 | char  *argv[];
194                  getevent();             /* main loop */
195   userr:
196          fprintf(stderr,
197 <        "Usage: %s [-geometry spec][-b][-m][-d][-f][-c ncolors][-e +/-stops] file\n",
197 >        "Usage: %s [-display disp][-geometry spec][-b][-m][-d][-f][-c ncolors][-e +/-stops] file\n",
198                          progname);
199          quit(1);
200   }
# Line 188 | Line 203 | userr:
203   headline(s)             /* get relevant info from header */
204   char  *s;
205   {
191        static char  *altname[] = {"rview","rpict","pinterp",VIEWSTR,NULL};
192        register char  **an;
206          char  fmt[32];
207  
208          if (isexpos(s))
# Line 197 | Line 210 | char  *s;
210          else if (isformat(s)) {
211                  formatval(fmt, s);
212                  wrongformat = strcmp(fmt, COLRFMT);
213 <        } else
214 <                for (an = altname; *an != NULL; an++)
202 <                        if (!strncmp(*an, s, strlen(*an))) {
203 <                                if (sscanview(&ourview, s+strlen(*an)) > 0)
204 <                                        gotview++;
205 <                                return;
206 <                        }
213 >        } else if (isview(s) && sscanview(&ourview, s) > 0)
214 >                gotview++;
215   }
216  
217  
# Line 211 | Line 219 | init()                 /* get data and open window */
219   {
220          XWMHints        ourxwmhints;
221          XSetWindowAttributes    ourwinattr;
222 <        XSizeHints  oursizhints;
223 <        register int  i;
222 >        XSizeHints      oursizhints;
223 >        register int    i;
224          
225          if (fname != NULL) {
226                  scanpos = (long *)malloc(ymax*sizeof(long));
# Line 221 | Line 229 | init()                 /* get data and open window */
229                  for (i = 0; i < ymax; i++)
230                          scanpos[i] = -1;
231          }
232 <        if ((thedisplay = XOpenDisplay(NULL)) == NULL)
233 <                quiterr("can't open display; DISPLAY variable set?");
234 <        if (maxcolors == 0) {           /* get number of available colors */
235 <                i = DisplayPlanes(thedisplay,ourscreen);
228 <                maxcolors = i > 8 ? 256 : 1<<i;
229 <                if (maxcolors > 4) maxcolors -= 2;
230 <        }
232 >        if ((thedisplay = XOpenDisplay(dispname)) == NULL)
233 >                quiterr("cannot open display");
234 >                                /* get best visual for default screen */
235 >        getbestvis();
236                                  /* store image */
237          getras();
238                                  /* open window */
239          ourwinattr.border_pixel = ourblack;
240          ourwinattr.background_pixel = ourwhite;
241 +        ourwinattr.colormap = XCreateColormap(thedisplay, ourroot,
242 +                        ourvis.visual, AllocNone);
243          wind = XCreateWindow(thedisplay, ourroot, 0, 0, xmax, ymax, BORWIDTH,
244 <                        0, InputOutput, ourras->visual,
245 <                        CWBackPixel|CWBorderPixel, &ourwinattr);
244 >                        ourvis.depth, InputOutput, ourvis.visual,
245 >                        CWBackPixel|CWBorderPixel|CWColormap, &ourwinattr);
246          if (wind == 0)
247 <                quiterr("can't create window");
247 >                quiterr("cannot create window");
248 >        XFreeColormap(thedisplay, ourwinattr.colormap);
249          width = xmax;
250          height = ymax;
251 +        ourgc = XCreateGC(thedisplay, wind, 0, 0);
252 +        XSetState(thedisplay, ourgc, ourblack, ourwhite, GXcopy, AllPlanes);
253 +        revgc = XCreateGC(thedisplay, wind, 0, 0);
254 +        XSetFunction(thedisplay, revgc, GXinvert);
255          fontid = XLoadFont(thedisplay, FONTNAME);
256          if (fontid == 0)
257 <                quiterr("can't get font");
257 >                quiterr("cannot get font");
258          XSetFont(thedisplay, ourgc, fontid);
247        revgc = XCreateGC(thedisplay, wind, 0, 0);
248        XSetFunction(thedisplay, revgc, GXinvert);
259          XDefineCursor(thedisplay, wind, XCreateFontCursor(thedisplay,
260                          XC_diamond_cross));
261 +        XStoreName(thedisplay, wind, fname == NULL ? progname : fname);
262          if (geometry != NULL) {
263                  bzero((char *)&oursizhints, sizeof(oursizhints));
264                  i = XParseGeometry(geometry, &oursizhints.x, &oursizhints.y,
# Line 280 | Line 291 | init()                 /* get data and open window */
291                          |ButtonMotionMask|StructureNotifyMask
292                          |KeyPressMask|ExposureMask);
293          XMapWindow(thedisplay, wind);
283                                /* store name last as ready signal */
284        XStoreName(thedisplay, wind, fname == NULL ? progname : fname);
294          return;
295   memerr:
296          quiterr("out of memory");
# Line 313 | Line 322 | int  code;
322   }
323  
324  
325 + static int
326 + viscmp(v1,v2)           /* compare visual to see which is better, descending */
327 + register XVisualInfo    *v1, *v2;
328 + {
329 +        int     bad1 = 0, bad2 = 0;
330 +        register int  *rp;
331 +
332 +        if (v1->class == v2->class) {
333 +                if (v1->class == TrueColor || v1->class == DirectColor) {
334 +                                        /* prefer 24-bit to 32-bit */
335 +                        if (v1->depth == 24 && v2->depth == 32)
336 +                                return(-1);
337 +                        if (v1->depth == 32 && v2->depth == 24)
338 +                                return(1);
339 +                        return(0);
340 +                }
341 +                                        /* don't be too greedy */
342 +                if (maxcolors <= 1<<v1->depth && maxcolors <= 1<<v2->depth)
343 +                        return(v1->depth - v2->depth);
344 +                return(v2->depth - v1->depth);
345 +        }
346 +                                        /* prefer Pseudo when < 24-bit */
347 +        if ((v1->class == TrueColor || v1->class == DirectColor) &&
348 +                        v1->depth < 24)
349 +                bad1 = 1;
350 +        if ((v2->class == TrueColor || v2->class == DirectColor) &&
351 +                        v2->depth < 24)
352 +                bad2 = -1;
353 +        if (bad1 | bad2)
354 +                return(bad1+bad2);
355 +                                        /* otherwise, use class ranking */
356 +        for (rp = ourrank; *rp != -1; rp++) {
357 +                if (v1->class == *rp)
358 +                        return(-1);
359 +                if (v2->class == *rp)
360 +                        return(1);
361 +        }
362 +        return(0);
363 + }
364 +
365 +
366 + getbestvis()                    /* get the best visual for this screen */
367 + {
368 + #ifdef DEBUG
369 + static char  vistype[][12] = {
370 +                "StaticGray",
371 +                "GrayScale",
372 +                "StaticColor",
373 +                "PseudoColor",
374 +                "TrueColor",
375 +                "DirectColor"
376 + };
377 + #endif
378 +        static int      rankings[3][6] = {
379 +                {TrueColor,DirectColor,PseudoColor,GrayScale,StaticGray,-1},
380 +                {PseudoColor,GrayScale,StaticGray,-1},
381 +                {PseudoColor,GrayScale,StaticGray,-1}
382 +        };
383 +        XVisualInfo     *xvi;
384 +        int     vismatched;
385 +        register int    i, j;
386 +
387 +        if (greyscale) {
388 +                ourrank = rankings[2];
389 +                if (maxcolors < 2) maxcolors = 256;
390 +        } else if (maxcolors >= 2 && maxcolors <= 256)
391 +                ourrank = rankings[1];
392 +        else {
393 +                ourrank = rankings[0];
394 +                maxcolors = 256;
395 +        }
396 +                                        /* find best visual */
397 +        ourvis.screen = ourscreen;
398 +        xvi = XGetVisualInfo(thedisplay,VisualScreenMask,&ourvis,&vismatched);
399 +        if (xvi == NULL)
400 +                quiterr("no visuals for this screen!");
401 + #ifdef DEBUG
402 +        fprintf(stderr, "Supported visuals:\n");
403 +        for (i = 0; i < vismatched; i++)
404 +                fprintf(stderr, "\ttype %s, depth %d\n",
405 +                                vistype[xvi[i].class], xvi[i].depth);
406 + #endif
407 +        for (i = 0, j = 1; j < vismatched; j++)
408 +                if (viscmp(&xvi[i],&xvi[j]) > 0)
409 +                        i = j;
410 +                                        /* compare to least acceptable */
411 +        for (j = 0; ourrank[j++] != -1; )
412 +                ;
413 +        ourvis.class = ourrank[--j];
414 +        ourvis.depth = 1;
415 +        if (viscmp(&xvi[i],&ourvis) > 0)
416 +                quiterr("inadequate visuals on this screen");
417 +                                        /* OK, we'll use it */
418 +        copystruct(&ourvis, &xvi[i]);
419 + #ifdef DEBUG
420 +        fprintf(stderr, "Selected visual type %s, depth %d\n",
421 +                        vistype[ourvis.class], ourvis.depth);
422 + #endif
423 +                                        /* make appropriate adjustments */
424 +        if (ourvis.class == GrayScale || ourvis.class == StaticGray)
425 +                greyscale = 1;
426 +        if (ourvis.depth <= 8 && ourvis.colormap_size < maxcolors)
427 +                maxcolors = ourvis.colormap_size;
428 +        if (ourvis.class == StaticGray) {
429 +                ourblack = 0;
430 +                ourwhite = 255;
431 +        } else if (ourvis.class == PseudoColor) {
432 +                ourblack = BlackPixel(thedisplay,ourscreen);
433 +                ourwhite = WhitePixel(thedisplay,ourscreen);
434 +                if ((ourblack|ourwhite) & ~255L) {
435 +                        ourblack = 0;
436 +                        ourwhite = 1;
437 +                }
438 +                if (maxcolors > 4)
439 +                        maxcolors -= 2;
440 +        } else {
441 +                ourblack = 0;
442 +                ourwhite = ourvis.red_mask|ourvis.green_mask|ourvis.blue_mask;
443 +        }
444 +        XFree((char *)xvi);
445 + }
446 +
447 +
448   getras()                                /* get raster file */
449   {
318        colormap        ourmap;
450          XVisualInfo     vinfo;
451  
452          if (maxcolors <= 2) {           /* monochrome */
453                  ourdata = (unsigned char *)malloc(ymax*((xmax+7)/8));
454                  if (ourdata == NULL)
455                          goto fail;
456 <                ourras = make_raster(thedisplay, ourscreen, 1, ourdata,
456 >                ourras = make_raster(thedisplay, &ourvis, 1, ourdata,
457                                  xmax, ymax, 8);
458                  if (ourras == NULL)
459                          goto fail;
460                  getmono();
461 <        } else if (XMatchVisualInfo(thedisplay,ourscreen,24,TrueColor,&vinfo)
462 <                                                /* kludge for DirectColor */
332 <        || XMatchVisualInfo(thedisplay,ourscreen,24,DirectColor,&vinfo)) {
333 <                ourdata = (unsigned char *)malloc(xmax*ymax*3);
461 >        } else if (ourvis.class == TrueColor | ourvis.class == DirectColor) {
462 >                ourdata = (unsigned char *)malloc(4*xmax*ymax);
463                  if (ourdata == NULL)
464                          goto fail;
465 <                ourras = make_raster(thedisplay, ourscreen, 24, ourdata,
466 <                                xmax, ymax, 8);
465 >                ourras = make_raster(thedisplay, &ourvis, 32,
466 >                                ourdata, xmax, ymax, 32);
467                  if (ourras == NULL)
468                          goto fail;
469                  getfull();
# Line 342 | Line 471 | getras()                               /* get raster file */
471                  ourdata = (unsigned char *)malloc(xmax*ymax);
472                  if (ourdata == NULL)
473                          goto fail;
474 <                ourras = make_raster(thedisplay, ourscreen, 8, ourdata,
474 >                ourras = make_raster(thedisplay, &ourvis, 8, ourdata,
475                                  xmax, ymax, 8);
476                  if (ourras == NULL)
477                          goto fail;
478 <                if (greyscale)
479 <                        biq(dither,maxcolors,1,ourmap);
478 >                if (greyscale | ourvis.class == StaticGray)
479 >                        getgrey();
480                  else
481 <                        ciq(dither,maxcolors,1,ourmap);
482 <                if (init_rcolors(ourras, ourmap[0], ourmap[1], ourmap[2]) == 0)
481 >                        getmapped();
482 >                if (ourvis.class != StaticGray && !init_rcolors(ourras,clrtab))
483                          goto fail;
484          }
485          return;
# Line 381 | Line 510 | getevent()                             /* process the next event */
510          case MapNotify:
511                  map_rcolors(ourras, wind);
512                  if (fast)
513 <                        make_rpixmap(ourras);
513 >                        make_rpixmap(ourras, wind);
514                  break;
515          case UnmapNotify:
516 <                unmap_rcolors(ourras);
516 >                if (!fast)
517 >                        unmap_rcolors(ourras);
518                  break;
519          case Expose:
520                  redraw(e.e.x, e.e.y, e.e.width, e.e.height);
# Line 407 | Line 537 | XKeyPressedEvent  *ekey;
537          XColor  cvx;
538          int  com, n;
539          double  comp;
540 +        FLOAT  hv[2];
541          FVECT  rorg, rdir;
542  
543          n = XLookupString(ekey, buf, sizeof(buf), NULL, NULL);
# Line 415 | Line 546 | XKeyPressedEvent  *ekey;
546          com = buf[0];
547          switch (com) {                  /* interpret command */
548          case 'q':
549 <        case CTRL(D):                           /* quit */
549 >        case CTRL('D'):                         /* quit */
550                  quit(0);
551          case '\n':
552          case '\r':
# Line 455 | Line 586 | XKeyPressedEvent  *ekey;
586                  XStoreColor(thedisplay, ourras->cmap, &cvx);
587                  return(0);
588          case 'p':                               /* position */
589 <                sprintf(buf, "(%d,%d)", ekey->x-xoff, ymax-1-ekey->y+yoff);
589 >                pix2loc(hv, &inpres, ekey->x-xoff, ekey->y-yoff);
590 >                sprintf(buf, "(%d,%d)", (int)(hv[0]*inpres.xr),
591 >                                (int)(hv[1]*inpres.yr));
592                  XDrawImageString(thedisplay, wind, ourgc, ekey->x, ekey->y,
593                                          buf, strlen(buf));
594                  return(0);
# Line 464 | Line 597 | XKeyPressedEvent  *ekey;
597                          XBell(thedisplay, 0);
598                          return(-1);
599                  }
600 <                if (viewray(rorg, rdir, &ourview,
601 <                                (ekey->x-xoff+.5)/xmax,
469 <                                (ymax-1-ekey->y+yoff+.5)/ymax) < 0)
600 >                pix2loc(hv, &inpres, ekey->x-xoff, ekey->y-yoff);
601 >                if (viewray(rorg, rdir, &ourview, hv[0], hv[1]) < 0)
602                          return(-1);
603                  printf("%e %e %e ", rorg[0], rorg[1], rorg[2]);
604                  printf("%e %e %e\n", rdir[0], rdir[1], rdir[2]);
# Line 488 | Line 620 | XKeyPressedEvent  *ekey;
620                  free_raster(ourras);
621                  getras();
622          /* fall through */
623 <        case CTRL(R):                           /* redraw */
624 <        case CTRL(L):
623 >        case CTRL('R'):                         /* redraw */
624 >        case CTRL('L'):
625                  unmap_rcolors(ourras);
626                  XClearWindow(thedisplay, wind);
627                  map_rcolors(ourras, wind);
628                  if (fast)
629 <                        make_rpixmap(ourras);
629 >                        make_rpixmap(ourras, wind);
630                  redraw(0, 0, width, height);
631                  return(0);
632          case ' ':                               /* clear */
# Line 581 | Line 713 | int  x0, y0, x1, y1;
713   avgbox(clr)                             /* average color over current box */
714   COLOR  clr;
715   {
716 +        static COLOR  lc;
717 +        static int  ll, lr, lt, lb;
718          int  left, right, top, bottom;
719          int  y;
720          double  d;
# Line 604 | Line 738 | COLOR  clr;
738                  bottom = ymax;
739          if (top >= bottom)
740                  return(-1);
741 +        if (left == ll && right == lr && top == lt && bottom == lb) {
742 +                copycolor(clr, lc);
743 +                return;
744 +        }
745          for (y = top; y < bottom; y++) {
746                  if (getscan(y) == -1)
747                          return(-1);
# Line 614 | Line 752 | COLOR  clr;
752          }
753          d = 1.0/((right-left)*(bottom-top));
754          scalecolor(clr, d);
755 +        ll = left; lr = right; lt = top; lb = bottom;
756 +        copycolor(lc, clr);
757          return(0);
758   }
759  
# Line 622 | Line 762 | getmono()                      /* get monochrome data */
762   {
763          register unsigned char  *dp;
764          register int    x, err;
765 <        int     y;
765 >        int     y, errp;
766          short   *cerr;
767  
768          if ((cerr = (short *)calloc(xmax,sizeof(short))) == NULL)
# Line 637 | Line 777 | getmono()                      /* get monochrome data */
777                  for (x = 0; x < xmax; x++) {
778                          if (!(x&7))
779                                  *++dp = 0;
780 +                        errp = err;
781                          err += normbright(scanline[x]) + cerr[x];
782                          if (err > 127)
783                                  err -= 255;
784                          else
785                                  *dp |= 1<<(7-(x&07));
786 <                        cerr[x] = err >>= 1;
786 >                        err /= 3;
787 >                        cerr[x] = err + errp;
788                  }
789          }
790          free((char *)cerr);
# Line 653 | Line 795 | add2icon(y, scan)              /* add a scanline to our icon data
795   int  y;
796   COLR  *scan;
797   {
656        static char  *dp = NULL;
798          static short  cerr[ICONSIZ];
799 +        static int  ynext;
800 +        static char  *dp;
801          register int  err;
802 <        register int    x, xi;
802 >        register int    x, ti;
803 >        int  errp;
804  
805          if (iconheight == 0) {          /* initialize */
806                  if (xmax <= ICONSIZ && ymax <= ICONSIZ) {
# Line 665 | Line 809 | COLR  *scan;
809                  } else if (xmax > ymax) {
810                          iconwidth = ICONSIZ;
811                          iconheight = ICONSIZ*ymax/xmax;
812 +                        if (iconheight < 1)
813 +                                iconheight = 1;
814                  } else {
815                          iconwidth = ICONSIZ*xmax/ymax;
816 +                        if (iconwidth < 1)
817 +                                iconwidth = 1;
818                          iconheight = ICONSIZ;
819                  }
820 +                ynext = 0;
821                  dp = icondata - 1;
822          }
823 <        if (dp == NULL)                 /* done already */
823 >        if (y < ynext*ymax/iconheight)  /* skip this one */
824                  return;
676        if (y % (ymax/iconheight))      /* skip this one */
677                return;
825          err = 0;
826          for (x = 0; x < iconwidth; x++) {
827                  if (!(x&7))
828                          *++dp = 0;
829 <                xi = x*xmax/iconwidth;
830 <                err += normbright(scan[xi]) + cerr[x];
829 >                errp = err;
830 >                ti = x*xmax/iconwidth;
831 >                err += normbright(scan[ti]) + cerr[x];
832                  if (err > 127)
833                          err -= 255;
834                  else
835                          *dp |= 1<<(x&07);
836 <                cerr[x] = err >>= 1;
836 >                err /= 3;
837 >                cerr[x] = err + errp;
838          }
839 <        if (y >= ymax - ymax/iconheight)        /* all done */
691 <                dp = NULL;
839 >        ynext++;
840   }
841  
842  
843   getfull()                       /* get full (24-bit) data */
844   {
845          int     y;
846 +        register unsigned long  *dp;
847 +        register int    x;
848 +                                        /* set gamma correction */
849 +        setcolrgam(gamcor);
850 +                                        /* read and convert file */
851 +        dp = (unsigned long *)ourdata;
852 +        for (y = 0; y < ymax; y++) {
853 +                if (getscan(y) < 0)
854 +                        quiterr("seek error in getfull");
855 +                if (scale)
856 +                        shiftcolrs(scanline, xmax, scale);
857 +                colrs_gambs(scanline, xmax);
858 +                add2icon(y, scanline);
859 +                if (ourras->image->blue_mask & 1)
860 +                        for (x = 0; x < xmax; x++)
861 +                                *dp++ = scanline[x][RED] << 16 |
862 +                                        scanline[x][GRN] << 8 |
863 +                                        scanline[x][BLU] ;
864 +                else
865 +                        for (x = 0; x < xmax; x++)
866 +                                *dp++ = scanline[x][RED] |
867 +                                        scanline[x][GRN] << 8 |
868 +                                        scanline[x][BLU] << 16 ;
869 +        }
870 + }
871 +
872 +
873 + getgrey()                       /* get greyscale data */
874 + {
875 +        int     y;
876          register unsigned char  *dp;
877          register int    x;
878                                          /* set gamma correction */
# Line 703 | Line 881 | getfull()                      /* get full (24-bit) data */
881          dp = ourdata;
882          for (y = 0; y < ymax; y++) {
883                  if (getscan(y) < 0)
884 <                        quiterr("seek error in getfull");
884 >                        quiterr("seek error in getgrey");
885                  if (scale)
886                          shiftcolrs(scanline, xmax, scale);
887                  colrs_gambs(scanline, xmax);
888                  add2icon(y, scanline);
889 <                for (x = 0; x < xmax; x++) {
890 <                        *dp++ = scanline[x][RED];
891 <                        *dp++ = scanline[x][GRN];
892 <                        *dp++ = scanline[x][BLU];
893 <                }
889 >                if (maxcolors < 256)
890 >                        for (x = 0; x < xmax; x++)
891 >                                *dp++ = ((long)normbright(scanline[x]) *
892 >                                        maxcolors + 128) >> 8;
893 >                else
894 >                        for (x = 0; x < xmax; x++)
895 >                                *dp++ = normbright(scanline[x]);
896          }
897 +        for (x = 0; x < maxcolors; x++)
898 +                clrtab[x][RED] = clrtab[x][GRN] =
899 +                        clrtab[x][BLU] = (x*256+maxcolors/2)/maxcolors;
900   }
901  
902  
903 + getmapped()                     /* get color-mapped data */
904 + {
905 +        int     y;
906 +                                        /* set gamma correction */
907 +        setcolrgam(gamcor);
908 +                                        /* make histogram */
909 +        new_histo();
910 +        for (y = 0; y < ymax; y++) {
911 +                if (getscan(y) < 0)
912 +                        quiterr("seek error in getmapped");
913 +                if (scale)
914 +                        shiftcolrs(scanline, xmax, scale);
915 +                colrs_gambs(scanline, xmax);
916 +                add2icon(y, scanline);
917 +                cnt_colrs(scanline, xmax);
918 +        }
919 +                                        /* map pixels */
920 +        if (!new_clrtab(maxcolors))
921 +                quiterr("cannot create color map");
922 +        for (y = 0; y < ymax; y++) {
923 +                if (getscan(y) < 0)
924 +                        quiterr("seek error in getmapped");
925 +                if (scale)
926 +                        shiftcolrs(scanline, xmax, scale);
927 +                colrs_gambs(scanline, xmax);
928 +                if (dither)
929 +                        dith_colrs(ourdata+y*xmax, scanline, xmax);
930 +                else
931 +                        map_colrs(ourdata+y*xmax, scanline, xmax);
932 +        }
933 + }
934 +
935 +
936   scale_rcolors(xr, sf)                   /* scale color map */
937   register XRASTER        *xr;
938   double  sf;
# Line 754 | Line 970 | int  y;
970                  if (fseek(fin, scanpos[y], 0) == -1)
971                          quiterr("fseek error");
972                  cury = y;
973 <        } else if (scanpos != NULL)
973 >        } else if (scanpos != NULL && scanpos[y] == -1)
974                  scanpos[y] = ftell(fin);
975  
976          if (freadcolrs(scanline, xmax, fin) < 0)
# Line 762 | Line 978 | int  y;
978  
979          cury++;
980          return(0);
765 }
766
767
768 picreadline3(y, l3)                     /* read in 3-byte scanline */
769 int  y;
770 register rgbpixel  *l3;
771 {
772        register int    i;
773                                                        /* read scanline */
774        if (getscan(y) < 0)
775                quiterr("cannot seek for picreadline");
776                                                        /* convert scanline */
777        normcolrs(scanline, xmax, scale);
778        add2icon(y, scanline);
779        for (i = 0; i < xmax; i++) {
780                l3[i].r = scanline[i][RED];
781                l3[i].g = scanline[i][GRN];
782                l3[i].b = scanline[i][BLU];
783        }
784 }
785
786
787 picwriteline(y, l)              /* add 8-bit scanline to image */
788 int  y;
789 pixel  *l;
790 {
791        bcopy((char *)l, (char *)ourdata+y*xmax, xmax);
792 }
793
794
795 picreadcm(map)                  /* do gamma correction */
796 colormap  map;
797 {
798        extern double  pow();
799        register int  i, val;
800
801        for (i = 0; i < 256; i++) {
802                val = pow((i+0.5)/256.0, 1.0/gamcor) * 256.0;
803                map[0][i] = map[1][i] = map[2][i] = val;
804        }
805 }
806
807
808 picwritecm(map)                 /* handled elsewhere */
809 colormap  map;
810 {
811 #ifdef DEBUG
812        register int i;
813
814        for (i = 0; i < 256; i++)
815                printf("%d %d %d\n", map[0][i],map[1][i],map[2][i]);
816 #endif
981   }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines