001: /*
002: * $RCSfile: LookupDescriptor.java,v $
003: *
004: * Copyright (c) 2005 Sun Microsystems, Inc. All rights reserved.
005: *
006: * Use is subject to license terms.
007: *
008: * $Revision: 1.1 $
009: * $Date: 2005/02/11 04:57:38 $
010: * $State: Exp $
011: */
012: package javax.media.jai.operator;
013:
014: import java.awt.RenderingHints;
015: import java.awt.image.DataBuffer;
016: import java.awt.image.RenderedImage;
017: import java.awt.image.renderable.ParameterBlock;
018: import java.awt.image.renderable.RenderableImage;
019: import javax.media.jai.JAI;
020: import javax.media.jai.LookupTableJAI;
021: import javax.media.jai.OperationDescriptorImpl;
022: import javax.media.jai.ParameterBlockJAI;
023: import javax.media.jai.RenderableOp;
024: import javax.media.jai.RenderedOp;
025: import javax.media.jai.registry.RenderableRegistryMode;
026: import javax.media.jai.registry.RenderedRegistryMode;
027:
028: /**
029: * An <code>OperationDescriptor</code> describing the "Lookup" operation.
030: *
031: * <p> The Lookup operation takes a rendered or renderable image and a
032: * lookup table, and performs general table lookup by passing the
033: * source image through the table.
034: *
035: * <p> The source may be a single- or multi-banded image of data types
036: * <code>byte</code>, <code>ushort</code>, <code>short</code>, or
037: * <code>int</code>. The lookup table may be single- or multi-banded
038: * and of any JAI supported data types. The destination image must have
039: * the same data type as the lookup table, and its number of bands is
040: * determined based on the number of bands of the source and the table.
041: * If the source is single-banded, the destination has the same number
042: * of bands as the lookup table; otherwise, the destination has the
043: * same number of bands as the source.
044: *
045: * <p> If either the source or the table is single-banded and the other
046: * one is multi-banded, then the single band is applied to every band
047: * of the multi-banded object. If both are multi-banded, then their
048: * corresponding bands are matched up.
049: *
050: * <p> The table may have a set of offset values, one for each band. This
051: * value is subtracted from the source pixel values before indexing into
052: * the table data array.
053: *
054: * <p> It is the user's responsibility to make certain the lookup table
055: * supplied is suitable for the source image. Specifically, the table
056: * data covers the entire range of the source data. Otherwise, the result
057: * of this operation is undefined.
058: *
059: * <p >By the nature of this operation, the destination may have a
060: * different number of bands and/or data type from the source. The
061: * <code>SampleModel</code> of the destination is created in accordance
062: * with the actual lookup table used in a specific case.
063: *
064: * <p> The destination pixel values are defined by the pseudocode:
065: * <ul>
066: * <li> If the source image is single-banded and the lookup table is
067: * single- or multi-banded, then the destination image has the same
068: * number of bands as the lookup table:
069: * <pre>
070: * dst[x][y][b] = table[b][src[x][y][0] - offsets[b]]
071: * </pre>
072: * </li>
073: *
074: * <li> If the source image is multi-banded and the lookup table is
075: * single-banded, then the destination image has the same number of
076: * bands as the source image:
077: * <pre>
078: * dst[x][y][b] = table[0][src[x][y][b] - offsets[0]]
079: * </pre>
080: * </li>
081: *
082: * <li> If the source image is multi-banded and the lookup table is
083: * multi-banded, with the same number of bands as the source image,
084: * then the destination image will have the same number of bands as the
085: * source image:
086: * <pre>
087: * dst[x][y][b] = table[b][src[x][y][b] - offsets[b]]
088: * </pre>
089: * </li>
090: * </ul>
091: *
092: * <p><table border=1>
093: * <caption>Resource List</caption>
094: * <tr><th>Name</th> <th>Value</th></tr>
095: * <tr><td>GlobalName</td> <td>Lookup</td></tr>
096: * <tr><td>LocalName</td> <td>Lookup</td></tr>
097: * <tr><td>Vendor</td> <td>com.sun.media.jai</td></tr>
098: * <tr><td>Description</td> <td>Performs general table lookup on an
099: * image.</td></tr>
100: * <tr><td>DocURL</td> <td>http://java.sun.com/products/java-media/jai/forDevelopers/jai-apidocs/javax/media/jai/operator/LookupDescriptor.html</td></tr>
101: * <tr><td>Version</td> <td>1.0</td></tr>
102: * <tr><td>arg0Desc</td> <td>The lookup table the source image
103: * is passed through.</td></tr>
104: * </table></p>
105: *
106: * <p><table border=1>
107: * <caption>Parameter List</caption>
108: * <tr><th>Name</th> <th>Class Type</th>
109: * <th>Default Value</th></tr>
110: * <tr><td>table</td> <td>javax.media.jai.LookupTableJAI</td>
111: * <td>NO_PARAMETER_DEFAULT</td>
112: * </table></p>
113: *
114: * @see javax.media.jai.LookupTableJAI
115: * @see javax.media.jai.OperationDescriptor
116: */
117: public class LookupDescriptor extends OperationDescriptorImpl {
118:
119: /**
120: * The resource strings that provide the general documentation
121: * and specify the parameter list for this operation.
122: */
123: private static final String[][] resources = {
124: { "GlobalName", "Lookup" },
125: { "LocalName", "Lookup" },
126: { "Vendor", "com.sun.media.jai" },
127: { "Description", JaiI18N.getString("LookupDescriptor0") },
128: {
129: "DocURL",
130: "http://java.sun.com/products/java-media/jai/forDevelopers/jai-apidocs/javax/media/jai/operator/LookupDescriptor.html" },
131: { "Version", JaiI18N.getString("DescriptorVersion") },
132: { "arg0Desc", JaiI18N.getString("LookupDescriptor1") } };
133:
134: /** The parameter class list for this operation. */
135: private static final Class[] paramClasses = { javax.media.jai.LookupTableJAI.class };
136:
137: /** The parameter name list for this operation. */
138: private static final String[] paramNames = { "table" };
139:
140: /** The parameter default value list for this operation. */
141: private static final Object[] paramDefaults = { NO_PARAMETER_DEFAULT };
142:
143: private static final String[] supportedModes = { "rendered",
144: "renderable" };
145:
146: /** Constructor. */
147: public LookupDescriptor() {
148: super (resources, supportedModes, 1, paramNames, paramClasses,
149: paramDefaults, null);
150: }
151:
152: /**
153: * Validates the input source.
154: *
155: * <p> In addition to the standard checks performed by the
156: * superclass method, this method checks that the source image
157: * is of integral data type.
158: */
159: protected boolean validateSources(String modeName,
160: ParameterBlock args, StringBuffer msg) {
161: if (!super .validateSources(modeName, args, msg)) {
162: return false;
163: }
164:
165: if (!modeName.equalsIgnoreCase("rendered"))
166: return true;
167:
168: RenderedImage src = args.getRenderedSource(0);
169:
170: int dtype = src.getSampleModel().getDataType();
171:
172: if (dtype != DataBuffer.TYPE_BYTE
173: && dtype != DataBuffer.TYPE_USHORT
174: && dtype != DataBuffer.TYPE_SHORT
175: && dtype != DataBuffer.TYPE_INT) {
176: msg.append(getName() + " "
177: + JaiI18N.getString("LookupDescriptor2"));
178: return false;
179: }
180:
181: return true;
182: }
183:
184: /**
185: * Performs general table lookup on an image.
186: *
187: * <p>Creates a <code>ParameterBlockJAI</code> from all
188: * supplied arguments except <code>hints</code> and invokes
189: * {@link JAI#create(String,ParameterBlock,RenderingHints)}.
190: *
191: * @see JAI
192: * @see ParameterBlockJAI
193: * @see RenderedOp
194: *
195: * @param source0 <code>RenderedImage</code> source 0.
196: * @param table The lookup table the source image is passed through.
197: * @param hints The <code>RenderingHints</code> to use.
198: * May be <code>null</code>.
199: * @return The <code>RenderedOp</code> destination.
200: * @throws IllegalArgumentException if <code>source0</code> is <code>null</code>.
201: * @throws IllegalArgumentException if <code>table</code> is <code>null</code>.
202: */
203: public static RenderedOp create(RenderedImage source0,
204: LookupTableJAI table, RenderingHints hints) {
205: ParameterBlockJAI pb = new ParameterBlockJAI("Lookup",
206: RenderedRegistryMode.MODE_NAME);
207:
208: pb.setSource("source0", source0);
209:
210: pb.setParameter("table", table);
211:
212: return JAI.create("Lookup", pb, hints);
213: }
214:
215: /**
216: * Performs general table lookup on an image.
217: *
218: * <p>Creates a <code>ParameterBlockJAI</code> from all
219: * supplied arguments except <code>hints</code> and invokes
220: * {@link JAI#createRenderable(String,ParameterBlock,RenderingHints)}.
221: *
222: * @see JAI
223: * @see ParameterBlockJAI
224: * @see RenderableOp
225: *
226: * @param source0 <code>RenderableImage</code> source 0.
227: * @param table The lookup table the source image is passed through.
228: * @param hints The <code>RenderingHints</code> to use.
229: * May be <code>null</code>.
230: * @return The <code>RenderableOp</code> destination.
231: * @throws IllegalArgumentException if <code>source0</code> is <code>null</code>.
232: * @throws IllegalArgumentException if <code>table</code> is <code>null</code>.
233: */
234: public static RenderableOp createRenderable(
235: RenderableImage source0, LookupTableJAI table,
236: RenderingHints hints) {
237: ParameterBlockJAI pb = new ParameterBlockJAI("Lookup",
238: RenderableRegistryMode.MODE_NAME);
239:
240: pb.setSource("source0", source0);
241:
242: pb.setParameter("table", table);
243:
244: return JAI.createRenderable("Lookup", pb, hints);
245: }
246: }
|