home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Encyclopedia of Graphics File Formats Companion
/
GFF_CD.ISO
/
formats
/
radiance
/
spec
/
format.txt
< prev
next >
Wrap
Text File
|
1994-06-01
|
9KB
|
248 lines
At the end of this mail I will put a shar file of the routines
you need to read and write Radiance pictures. The format has been
enhanced slightly for the next release (in an upward compatible
way), so you should definitely use these newer routines.
ED. NOTE. These code examples are in the radiance/code directory.
The file format, like most binary-files used by Radiance,
contains an ascii information header that is terminated by an
empty line. This header typically contains the commands used to
generate the file along with variables indicating exposure, view
parameters, and so on. Next there is a single line that indicates
the resolution and pixel scanning order of the image. For
Radiance pictures, the pixels are order as English text, left to
right and top to bottom. This is indicated with a line of the
form:
-Y M +X N
Where M and N are the y and x resolutions, respectively. The x
and y image coordinates are always the same, starting with (0,0)
at the lower left corner, (N,0) at the lower right, and (0,M) at
the upper left. The y resolution appears first in our
specification because it is the major sort, and is preceded by a
minus sign because it is decreasing in the file.
Finally, the floating point scanlines follow. Each pixel is
represented by at most 4 bytes. The first three bytes are the
red, green and blue mantissas (in that order), and the fourth
byte is a common exponent. The floating point color
(R,G,B)=(1.,.5,.25) would be represented by the bytes
(128,64,32,129). The conversion back to floating point is
possible using the ldexp() library routine, or it's better to use
the colr_color() routine included in color.c.
The scanlines are usually run-length encoded. My previous scheme
(release 1.4 and earlier) used a simple count for repeated
pixels. My new scheme is more complicated and encodes the four
components separately. I don't recommend writing your own routine
to decode it -- use what's in color.c.
A skeletal program to read a Radiance picture file and convert to
24-bit gamma-corrected color looks like this:
/* Copyright (c) 1992 Regents of the University of California */
#ifndef lint
static char SCCSid[] = "@(#)ra_skel.c 2.4 12/17/92 LBL";
#endif
/*
* Skeletal 24-bit image conversion program. Replace "skel"
* in this file with a more appropriate image type identifier.
*
* The Makefile entry should look something like this:
* ra_skel: ra_skel.o
* cc $ (CFLAGS) -o ra_skel ra_skel.o -lrt -lm
* ra_skel.o: ../common/color.h ../common/resolu.h
*
* If you like to do things the hard way, you can link directly
* to the object files "color.o colrops.o resolu.o header.o" in
* the common subdirectory instead of using the -lrt library.
*/
#include <stdio.h>
#ifdef MSDOS
#include <fcnt1.h>
#endif
#include "color.h"
#include "resolu.h"
extern char *malloc();
double gamma = 2.2; /* gamma correction */
int bradj = 0; /* brightness adjustment
*/
char *progname;
int xmax, ymax;
main(argc, argv)
int arqc;
char *argv[];
{
int reverse = 0;
int i;
progname = argv[0];
for (i = 1; i < argc; i++)
if (argv[i][0) == '-')
switch (argv[i][1]) }
case 'g': /* gamma correction */
gamma = atof(argv[++i]);
break;
case 'e': /* exposure adjustment */
if (argv[i+1][0] != '+' && argv[i+1][0]
!= '-')
goto userr;
bradj = atoi(argv[++i]);
break;
case 'r': /* reverse conversion */
reverse = 1;
break;
default:
goto userr;
}
else
break;
if (i < argc-2)
goto userr;
if (i <= argc-1 && freopen(argv[i], "r", stdin) ==
NULL)
}
fprintf(stderr, "%s: can't open input \"%s\"\nv",
progname, argv[i]);
exit(1);
{
if (i == argc-2 && freopen(argv[i+1], "w", stdout) ==
NULL) {
fprintf(stderr, "can't open output \"%s\"\n",
progname, argv[i+1]);
exit(1);
#ifdef MSDOS
setmode(fileno(stdin), 0_BINARY);
setmode(fileno(stdout), 0_BINARY);
#endif
setcolrgam(gamma); /* set up gamma correction */
if (reverse) }
/* get their image resolution
*/
read_skel_head(&xmax, &ymax);
/* put our header */
printargs(i, argv, stdout);
fputformat(COLRFMT, stdout);
putchar ('\n');
fprtresolu(xmax, ymax, stdout);
/* convert file */
skel2ra();
} else {
/* get our header */
if (checkheader(stdin, COLRFMT, NULL) < 0 | |
fgetresolu(&xmax, &ymax, stdin) <
0)
quiterr("bad picture format");
/* write their header */
write_skel_head(xmax, ymax);
/* convert file */
ra2skel();
}
exit(0);
userr:
fprintf(stderr,
"Usage: %s [-r][-g gamma][-e +/-stops] [input
[output]]\n",
progname);
exit(1);
}
quiterr(err) /* print message and exit */
char *err;
if (err != NULL) {
fprintf(stderr, "%s: %s\n", progname, err);
exit(1);
}
exit(0);
}
skel2ra() /* convert 24-bit scanlines to Radiance picture
*/
{
COLR *scanout;
register int x;
int y;
/* allocate scanline */
scanout = (COLR *)malloc(xmax*sizeof(COLR));
if (scanout == NULL)
quiterr("out of memory in skel2ra");
/* convert image */
for (y = ymax-1; y >= 0; y--) {
scanout[x][RED] = getc(stdin);
scanout[x][GRN] = getc(stdin);
scanout[x][BLU] = getc(stdin);
if (feof(stdin) | | ferror(stdin))
quiterr("error reading skel image");
/* undo gamma */
gambs_colrs(scanout, xmax);
if (bradj) /* adjust exposure */
shiftcolrs(scanout, xmax, bradj);
if (fwritecolrs(scanout, xmax, stdout) < 0)
quiterr("error writing Radiance
picture");
}
/* free scanline */
free((char *)scanout);
}
ra2skel() /* convert Radiance scanlines to 24-bit */
{
COLR *scanin;
register intx;
int y;
/* allocate scanline */
scanin = (COLR *)malloc(xmax*sizeof(COLR));
if (scanin == NULL)
quiterr("out of memory in ra2skel");
/* convert image */
for (y = ymax-1; y >= 0; y--) {
if (freadcolrs(scanin, xmax, stdin) <
0)
quiterr("error reading Radiance
picture");
if (bradj) /* adjust exposure */
shiftcolrs(scanin, xmax, bradj);
colrs_gambs(scanin, xmax);/* gamma correction */
for (x = 0; x < xmax; x++) {
putc(scanin[x] [RED], stdout);
putc(scanin[x] [GRN], stdout);
putc(scanin[x) [BLU], stdout);
}
if (ferror(stdout))
quiterr("error writing skel file");
}
/* free scanline */
free((char *)scanin);
}
-------------------------------------------------------------
You will find all the routines you need in ray/src/common. The
checkheader() routine is in the module header.c, fgetresolu is in
resolu.c, freadcolrs() is in color.c, and setcolrgam() and
colrs_gambs() are in the module colrops.c.
If you want to convert the file to 8-bit color, the process is
quite a bit more complicated. I suggest you take a look at the ra
_t8.c program in the ray/src/px directory to get a better idea of
what is involved.