CONTENTS | PREV | NEXT Java 2D API


5.8 Image Processing and Enhancement

The image package provides a pair of interfaces that define operations on BufferedImage and Raster objects: BufferedImageOp and RasterOp.

The classes that implement these interfaces include AffineTransformOp, BandCombineOp, ColorConvertOp, ConvolveOp, LookupOp, RescaleOp, and ThresholdOp. These classes can be used to geometrically transform, blur, sharpen, enhance contrast, threshold, and color correct images.

Figure 5-4 illustrates edge detection and enhancement, an operation that emphasizes sharp changes in intensity within an image. Edge detection is commonly used in medical imaging and mapping applications. Edge detection is used to increase the contrast between adjacent structures in an image, allowing the viewer to discriminate greater detail.

Figure 5-4 Edge detection and enhancement

Figure 5-5 demonstrates lookup table manipulation via rescaling and thresholding. Rescaling can increase or decrease the intensity of all points. Rescaling can be used to increase the dynamic range of an otherwise neutral image, bringing out detail in a region that appears neutral or flat. Thresholding can clip ranges of intensities to a specified level.

Figure 5-5 Lookup-table Manipulation


5.8.1 Using an Image Processing Operation

The following code fragment illustrates how to use one of the image processing classes, ConvolveOp. Convolution is the process that underlies most spatial filtering algorithms. Convolution is the process of weighting or averaging the value of each pixel in an image with the values of neighboring pixels.This allows each output pixel to be affected by the immediate neighborhood in a way that can be mathematically specified with a kernel.In this example, each pixel in the source image is averaged equally with the eight pixels that surround it.

float weight = 1.0f/9.0f;
float[] elements = new float[9]; // create 2D array

// fill the array with nine equal elements
for (i = 0; i < 9; i++) {
elements[i] = weight;
}
// use the array of elements as argument to create a Kernel
private Kernel myKernel = new Kernel(3, 3, elements);
public ConvolveOp simpleBlur = new ConvolveOp(myKernel);
// sourceImage and destImage are instances of BufferedImage
simpleBlur.filter(sourceImage, destImage) // blur the image
The variable simpleBlur contains a new instance of ConvolveOp that implements a blur operation on a BufferedImage or a Raster. Suppose that sourceImage and destImage are two instances of BufferedImage. When you call filter, the core method of the ConvolveOp class, it sets the value of each pixel in the destination image by averaging the corresponding pixel in the source image with the eight pixels that surround it.

The convolution kernel in this example could be represented by the following matrix, with elements specified to four significant figures:

When an image is convolved, the value of each pixel in the destination image is calculated by using the kernel as a set of weights to average the pixel's value with the values of surrounding pixels. This operation is performed on each channel of the image.

The following formula shows how the weights in the kernel are associated with the pixels in the source image when the convolution is performed. Each value in the kernel is tied to a spatial position in the image.

The value of a destination pixel is the sum of the products of the weights in the kernel multiplied by the value of the corresponding source pixel. For many simple operations, the kernel is a matrix that is square and symmetric, and the sum of its weights adds up to one.1

The convolution kernel in this example is relatively simple. It weights each pixel from the source image equally. By choosing a kernel that weights the source image at a higher or lower level, a program can increase or decrease the intensity of the destination image. The Kernel object, which is set in the ConvolveOp constructor, determines the type of filtering that is performed. By setting other values, you can perform other types of convolutions, including blurring (such as Gaussian blur, radial blur, and motion blur), sharpening, and smoothing operations.


5.8.2 Implementing an Image Processing Operation

In addition to using implementations of BufferedImageOp and RasterOp provided with the Java 2D imaging API, you can create custom image processing operations by implementing these two interfaces. The key methods of these interfaces are the BufferedImageOp.filter and RasterOp.filter methods. Both methods take a source and destination object.

Generally, you implement the filter methods by accessing and adjusting the individual pixels of image data provided in the source object. In some cases, you perform an analysis based solely on the pixel data itself. In these cases you can manipulate the data directly in the Image or Raster provided to you, and provide that object as the return value. In other cases, you perform analysis based on the pixel and its surrounding pixels. In these cases, you'll need to store the resulting pixel data in a new Image or Raster -- to avoid making the data inconsistent as you evaluate it.

Here's an example of a filtering operation that evaluates individual pixels:

<<sample code tbd>>
Here's an example of a filtering operation that evaluates each pixel and the eight pixels surrounding it to determine the output value for the pixel.

<<sample code tbd>>


CONTENTS | PREV | NEXT
Copyright © 1997-1998 Sun Microsystems, Inc. All Rights Reserved.