VistaIOImage(3) | Library Functions Manual | VistaIOImage(3) |
VistaIOImage - image representation
#include <vistaio.h>
VistaIOImage image;
Vista represents an image as one or more two-dimensional arrays of pixel values. Each two-dimensional array, called a band, has the same size, which is expressed as a number of rows and a number of columns. Multiple bands may, for example, be used to represent multiple color components, multiple frames of a motion sequence, the real and imaginary components of a complex image, or some combination of these. Besides pixel data, an image may also has an arbitrary list of attributes associated with it.
An image in memory is referred to by the C pointer type VistaIOImage. In data files it's identified by the type name image, and in memory, by the VistaIORepnKind code VistaIOImageRepn. Since it is a standard object type with built-in support in the Vista library, images can be read from data files, written to data files, and manipulated as part of attribute lists by routines such as VistaIOReadFile(3), VistaIOWriteFile(3), and VistaIOGetAttr(3).
The following routines create and destroy images.
VistaIOImage VistaIOCreateImage (int nbands, int nrows, int ncolumns, VistaIOPixelRepn pixel_repn)
void VistaIODestroyImage (VistaIOImage image)
An image's numbers of bands, row, and columns are sometimes abbreviated as nbands, nrows, and ncolumns. The following macros access those numbers.
int VistaIOImageNBands (VistaIOImage image)
int VistaIOImageNRows (VistaIOImage image)
int VistaIOImageNColumns (VistaIOImage image)
int VistaIOImageNPixels (VistaIOImage image)
An image's pixel values may have any of the following types: VistaIOBit, VistaIOUByte, VistaIOSByte, VistaIOShort, VistaIOLong, VistaIOFloat, or VistaIODouble. VistaIOariables meant to hold pixel values or pointers to pixel values should be defined using these same types (rather than built-in C types such as short and long) to ensure software portability.
The following macros return information about an image's pixel representation:
VistaIORepnKind VistaIOPixelRepn (VistaIOImage image)
size_t VistaIOPixelSize (VistaIOImage image)
int VistaIOPixelPrecision (VistaIOImage image)
VistaIOStringConst VistaIOPixelRepnName (VistaIOImage image)
VistaIODouble VistaIOPixelMaxValue (VistaIOImage image)
VistaIODouble VistaIOPixelMinValue (VistaIOImage image)
size_t VistaIOImageSize (VistaIOImage image)
A particular pixel value is indexed by a band number, a row number, and a column number. Bands, rows, and columns are numbered consecutively from zero. Rows number down and columns number to the right so that row 0, column 0 is at the upper-left corner of the image.
type VistaIOPixel (VistaIOImage image, int band, int row, int column, type)
VistaIOPointer VistaIOPixelPtr (VistaIOImage image, int band, int row, int column)
pixel = VistaIOPixelPtr (image, band, row, column); if (VistaIOPixelRepn (image) == VistaIOBitRepn)
* (VistaIOBit *) pixel = new_value;
else ...
type ** VistaIOPixelArray (VistaIOImage image, type)
VistaIOPixelArray returns a pointer that can be used to access any image pixel by indexing it first with the pixel's band number, then its row number, and then its column number. For example:
VistaIOUByte **pixels = VistaIOPixelArray (image, VistaIOUByte); pixels[band][row][column] = new_value;
VistaIOPointer VistaIOImageData (VistaIOImage image)
In addition to its pixel values an image may have any number of other attributes; they are represented as an attribute list.
VistaIOAttrList VistaIOImageAttrList (VistaIOImage image)
VistaIOImageAttrList is a macro for accessing the attribute list associated with an image. The macro may be used as an rvalue to reach attributes within the list:
VistaIOGetAttr (VistaIOImageAttrList (image), VistaIONameAttr, ...)
or as an lvalue to manipulate the entire list:
VistaIODestroyAttrList (VistaIOImageAttrList (image)); VistaIOImageAttrList (image) = VistaIOCopyAttrList (other_list);
The bands of a multi-band image might represent the successive frames of a motion sequence, the left and right halves of a stereo pair, or the red, green, and blue channels of a color image. They might even represent a combination of such dimensions — for example, a stereo pair of color images. Because a great many different uses of the bands are possible, each image includes information describing how its bands are to be interpreted. This information assigns each band an interpretation in terms of four dimensions:
Although these four dimensions do not account for all conceivable ways one might wish to use the bands of a multi-band image, they do cover most cases. The scheme can usually be adapted to cover cases not explicitly handled. For example, a collection of images obtained under various lighting conditions could be represented by using the frame dimension to index the lighting condition.
Each image specifies the sizes of its four band interpretation dimensions. For a stereo pair of color images, for example, the size of the viewpoint dimension is two, the size of the color dimension is three, and the remaining dimensions have sizes of one. The dimension sizes are often abbreviated as nframes, nviewpoints, ncolors, and ncomponents. Their product should always equal the number of bands in the image. These macros exist for accessing the sizes:
int VistaIOImageNFrames (VistaIOImage image)
int VistaIOImageNViewpoints (VistaIOImage image)
int VistaIOImageNColors (VistaIOImage image)
int VistaIOImageNComponents (VistaIOImage image)
Each macro may be used as rvalue to obtain the size of a dimension, or as an lvalue to set it.
The four dimensions are mapped onto the single dimension, band, according to a particular ordering: component varies most rapidly, then color, then viewpoint, and finally frame. A macro is available for computing this mapping:
int VistaIOBandIndex (VistaIOImage image, int frame, int viewpoint, int color, int component)
VistaIOBandIndex returns the index of the band that corresponds to a particular combination of frame, viewpoint, channel, and component indices.
An image's attribute list may include attributes indicating how the image employs the four band interpretation dimensions. One attribute for each dimension provides the first level of description. Its value is an integer code, with some standard codes defined for common uses. Below is a list of the four attributes and their standard values. Shown in are both the symbolic constants that can be used C programs to refer to the integer values, and (in parentheses) the keywords used to represent the values externally, in Vista data files.
frame_interp, which currently has no standard values defined for it
viewpoint_interp, which has this standard value:
color_interp, which has these standard values:
component_interp, which has these standard values:
To prevent accidental misspellings of the attribute names you should use these symbolic constants:
#define VistaIOFrameInterpAttr "frame_interp" #define VistaIOViewpointInterpAttr "viewpoint_interp" #define VistaIOColorInterpAttr "color_interp" #define VistaIOComponentInterpAttr "component_interp"
A dictionary, VistaIOBandInterpDict, defines the mapping between the band interpretation codes (e.g., VistaIOBandInterpComplex) and their keywords (e.g., complex):
VistaIODictEntry VistaIOBandInterpDict[];
For each of the four band interpretation dimensions there is a routine you can use to simultaneously check both the dimension's size and, if present, its interpretation attribute. The VistaIOBandInterp(3) man page describes the four routines.
Pixel aspect ratio is defined as the ratio of pixel width to pixel height. An image may include, on its attribute list, an attribute specifying this ratio as a floating point value. The attribute has the name pixel_aspect_ratio and a symbolic constant exists for referring to it:
#define VistaIOPixelAspectRatioAttr "pixel_aspect_ratio"
When the attribute is absent, a pixel aspect ratio of 1.0 is assumed.
A Vista library routine that processes one image to produce another usually takes three or more arguments, like this:
VistaIOImage VistaIOProcessImage (VistaIOImage src, VistaIOImage dest, VistaIOBand band)
The first argument specifies the source image to be processed. The second specifies the destination image, to contain the result. You generally have three choices for how this destination image is provided:
dest = VistaIOProcessImage (src, NULL, band);
dest = VistaIOCreateImageLike (src); VistaIOProcessImage (src, dest, band);
VistaIOProcessImage (src, src, band);
In all cases, the routine will return the destination image if successful, and NULL otherwise. Moreover, if NULL is returned, the routine will already have called VistaIOWarning(3) to issue a warning message describing the problem.
The third argument to most image processing routines, band, may specify a particular band of the source image to be processed; or it may be the constant VistaIOAllBands (defined as -1) to indicate that all bands of the source image are to be processed. When a particular band is specified, band must be at least 0 and less than the number of bands in the source image; the destination image will usually have a single band to contain the result. When VistaIOAllBands is specified, the destination image will usually have the same number of bands as the source image.
Normally a routine will copy the source image's attribute list to the destination image, replacing any attributes the destination image had already. The sizes of the four band interpretation dimensions (nframes, nviewpoints, etc.) are also copied. When appropriate, however, a routine may delete or modify the attributes and dimensional sizes as it copies them from source to destination. For example, a routine that converts an RGB color image to a grey-scale one (VistaIORGBImageToGray(3)) expects a source image with the properties ncolors: 3 and color_interp: rgb; the destination image it produces has ncolors: 1 and no color_interp attribute.
typedef struct {
int nbands; /* number of bands */ int nrows; /* number of rows */ int ncolumns; /* number of columns */ VistaIORepnKind pixel_repn; /* representation of pixel values */ unsigned long flags; /* various flags */ VistaIOAttrList attributes; /* list of other image attributes */ VistaIOPointer data; /* array of image pixel values */ VistaIOPointer *row_index; /* ptr to first pixel of each row */ VistaIOPointer *band_index; /* ptr to first row of each band */ int nframes; /* number of motion frames */ int nviewpoints; /* number of camera viewpoints */ int ncolors; /* number of color channels */ int ncomponents; /* number of vector components */
} VistaIOImageRec, *VistaIOImage;
An image is represented in memory by a value of type VistaIOImage, which points to a VistaIOImageRec structure. Programmers using images will usually not need to access this structure's fields directly from their code since there are Vista library routines and macros available for most purposes. However, when debugging, one may occasionally need to examine a VistaIOImageRec structure's fields directly. The following paragraphs describe the fields.
The nbands, nrows, and ncolumns fields of the structure describe how many bands, rows, and columns the image has. Its pixel_repn field specifies how the image's pixel values are represented; it contains one of the constants VistaIOBitRepn, VistaIOUByteRepn, VistaIOSByteRepn, VistaIOShortRepn, VistaIOLongRepn, VistaIOFloatRepn, or VistaIODoubleRepn. Its attributes field contains the list of attributes associated with the image.
An image's pixel values are stored in a contiguous block of memory where they are arranged as follows. Within each band pixel values are ordered, beginning with the pixel at row 0, column 0, proceeding to row 0, column 1, etc., and ending with the highest numbered row and column. Each band's array of pixel values occupies a separate block of memory, and these blocks are arranged contiguously. All of band 0's pixel values are first, followed by all of band 1's, etc. In summary, pixel values are ordered by band, then by row within each band, and then by column. The pixel values themselves are of type VistaIOBit, VistaIOUByte, ..., or VistaIODouble.
The data field of a VistaIOImageRec points to the block of memory containing pixel values. The row_index field points to a vector of pointers to the first pixel value of each row within each band; this vector is of length (nbands * nrows) and it is indexed by an expression of the form (band * nrows + row). The band_index field points to a vector of pointers to the first row_index entry of each band; this vector is of length nbands and it is indexed by band number.
Individual bits of a VistaIOImageRec's flags field are used to denote various things. One bit is currently defined:
The nframes, nviewpoints, ncolors, and ncomponents fields describe the number of motion frames, camera positions, color channels, and vector components that the image's various bands represent. Together they should account for all bands of the image — i.e., their product should equal nbands. The image's bands are ordered according to these fields, with component index incrementing most rapidly and frame index incrementing least rapidly.
attribute-name: image {
nbands: nbands nrows: nrows ncolumns: ncolumns repn: pixel-representation nframes: nframes nviewpoints: nviewpoints ncolors: ncolors ncomponents: ncomponents data: data-offset length: data-length other attributes
}
pixel-representation ::=
bit | ubyte | sbyte | short | long | float | double
An image is represented in a Vista data file as an attribute. The attribute's value is an object of type image containing the following attributes in any order:
An nbands, nframes, nviewpoints, ncolors, or ncomponents attribute may be omitted if its value is 1. Moreover, the image object's attribute list may contain any other attributes associated with the image. See, for example, the data file listed under ``EXAMPLES'', below.
Image pixel values are represented in binary form in the binary data section of a file. They occupy a contiguous block in which pixel values are ordered by band, row, and column, as in memory.
Single-bit pixel values are packed eight to a byte, beginning with the most-significant bit of each byte. Pixel values of more than 8 bits are packed into multiple bytes, beginning with the most-significant byte of the pixel value. Consecutive pixel values are packed together, without intervening bits for padding or alignment. If necessary, however, the entire block of pixel values is padded so that its length is a multiple of 8 bits.
Each kind of pixel is represented as follows in the Vista data file:
Note that a pixel's representation in a Vista data file is independent of the form it takes when stored in memory on any particular machine. Thus a VistaIOBit pixel may occupy 8 bits in the main memory of a Sun SPARCstation 32 bits on a Cray machine, but it always occupies a single bit in a Vista data file.
This code fragment sets all pixels with 1 in a one-band image of single-bit pixels:
The previous example may be made more efficient by avoiding the repeated computation of pixel addresses:
for (i = 0; i < VistaIOImageNPixels (image); i++)
This code fragment creates an image of complex pixel values:
VistaIOImageNFrames (image) = VistaIOImageNViewpoints (image) = VistaIOImageNColors (image) = 1;
VistaIOImageNComponents (image) = 2;
VistaIOSetAttr (VistaIOImageAttrList (image), VistaIOComponentInterpAttr, NULL, VistaIOLongRepn, (VistaIOLong) VistaIOBandInterpComplex);
Here is an example of a Vista data file containing two images:
V-data 2 {
one: image {
nbands: 2 nrows: 256 ncolumns: 256 ncomponents: 2 component_interp: complex repn: float data: offset of first image's pixel values length: 524288 name: "UFO sighted over VistaIOancouver" pixel_aspect_ratio: 1.25
} two: image {
nrows: 32 ncolumns: 32 repn: ubyte data: offset of second image's pixel values length: 128 name: "UFO icon"
}
} ^L first image's pixel values second image's pixel values
Art Pope <pope@cs.ubc.ca>
Adaption to vistaio: Gert Wollny <gw.fossdev@gmail.com>
The following table summarizes the Vista library routines that operate on images. Many of these routine are documented elsewhere, by a section 3 man page named for the routine.
For creating and destroying images in memory:
For fetching and storing pixel values:
For getting band interpretation information:
For reading and writing images:
For comparing images:
For copying images:
For converting an image's pixel representation:
For rotating or transposing an image:
For changing the size of an image:
For filtering and transforming images:
For computing image statistics:
For working with complex images:
For displaying or rendering images:
For filling images with patterns:
Miscellaneous:
12 April 1994 | VistaIO Version 1.2.14 |