KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > java > awt > image > SampleModel


1 /*
2  * @(#)SampleModel.java 1.36 03/12/19
3  *
4  * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
5  * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
6  */

7
8 /* ****************************************************************
9  ******************************************************************
10  ******************************************************************
11  *** COPYRIGHT (c) Eastman Kodak Company, 1997
12  *** As an unpublished work pursuant to Title 17 of the United
13  *** States Code. All rights reserved.
14  ******************************************************************
15  ******************************************************************
16  ******************************************************************/

17
18 package java.awt.image;
19
20 /**
21  * This abstract class defines an interface for extracting samples of pixels
22  * in an image. All image data is expressed as a collection of pixels.
23  * Each pixel consists of a number of samples. A sample is a datum
24  * for one band of an image and a band consists of all samples of a
25  * particular type in an image. For example, a pixel might contain
26  * three samples representing its red, green and blue components.
27  * There are three bands in the image containing this pixel. One band
28  * consists of all the red samples from all pixels in the
29  * image. The second band consists of all the green samples and
30  * the remaining band consists of all of the blue samples. The pixel
31  * can be stored in various formats. For example, all samples from
32  * a particular band can be stored contiguously or all samples from a
33  * single pixel can be stored contiguously.
34  * <p>
35  * Subclasses of SampleModel specify the types of samples they can
36  * represent (e.g. unsigned 8-bit byte, signed 16-bit short, etc.)
37  * and may specify how the samples are organized in memory.
38  * In the Java 2D(tm) API, built-in image processing operators may
39  * not operate on all possible sample types, but generally will work
40  * for unsigned integral samples of 16 bits or less. Some operators
41  * support a wider variety of sample types.
42  * <p>
43  * A collection of pixels is represented as a Raster, which consists of
44  * a DataBuffer and a SampleModel. The SampleModel allows access to
45  * samples in the DataBuffer and may provide low-level information that
46  * a programmer can use to directly manipulate samples and pixels in the
47  * DataBuffer.
48  * <p>
49  * This class is generally a fall back method for dealing with
50  * images. More efficient code will cast the SampleModel to the
51  * appropriate subclass and extract the information needed to directly
52  * manipulate pixels in the DataBuffer.
53  *
54  * @see java.awt.image.DataBuffer
55  * @see java.awt.image.Raster
56  * @see java.awt.image.ComponentSampleModel
57  * @see java.awt.image.PixelInterleavedSampleModel
58  * @see java.awt.image.BandedSampleModel
59  * @see java.awt.image.MultiPixelPackedSampleModel
60  * @see java.awt.image.SinglePixelPackedSampleModel
61  */

62
63 public abstract class SampleModel
64 {
65
66     /** Width in pixels of the region of image data that this SampleModel
67      * describes.
68      */

69     protected int width;
70
71     /** Height in pixels of the region of image data that this SampleModel
72      * describes.
73      */

74     protected int height;
75
76     /** Number of bands of the image data that this SampleModel describes. */
77     protected int numBands;
78
79     /** Data type of the DataBuffer storing the pixel data.
80      * @see java.awt.image.DataBuffer
81      */

82     protected int dataType;
83
84     static private native void initIDs();
85     static {
86         ColorModel.loadLibraries();
87         initIDs();
88     }
89
90     /**
91      * Constructs a SampleModel with the specified parameters.
92      * @param dataType The data type of the DataBuffer storing the pixel data.
93      * @param w The width (in pixels) of the region of image data.
94      * @param h The height (in pixels) of the region of image data.
95      * @param numBands The number of bands of the image data.
96      * @throws IllegalArgumentException if <code>w</code> or <code>h</code>
97      * is not greater than 0
98      * @throws IllegalArgumentException if the product of <code>w</code>
99      * and <code>h</code> is greater than
100      * <code>Integer.MAX_VALUE</code>
101      * @throws IllegalArgumentException if <code>dataType</code> is not
102      * one of the supported data types
103      */

104     public SampleModel(int dataType, int w, int h, int numBands)
105     {
106         float size = (float)w*h;
107         if (w <= 0 || h <= 0) {
108             throw new IllegalArgumentException JavaDoc("Width ("+w+") and height ("+
109                                                h+") must be > 0");
110         }
111         if (size >= Integer.MAX_VALUE) {
112             throw new IllegalArgumentException JavaDoc("Dimensions (width="+w+
113                                                " height="+h+") are too large");
114         }
115
116         if (dataType < DataBuffer.TYPE_BYTE ||
117             (dataType > DataBuffer.TYPE_DOUBLE &&
118              dataType != DataBuffer.TYPE_UNDEFINED))
119         {
120             throw new IllegalArgumentException JavaDoc("Unsupported dataType: "+
121                                                dataType);
122         }
123
124         if (numBands <= 0) {
125             throw new IllegalArgumentException JavaDoc("Number of bands must be > 0");
126         }
127         
128     this.dataType = dataType;
129     this.width = w;
130     this.height = h;
131     this.numBands = numBands;
132     }
133
134     /** Returns the width in pixels.
135      * @return the width in pixels of the region of image data
136      * that this <code>SampleModel</code> describes.
137      */

138     final public int getWidth() {
139      return width;
140     }
141
142     /** Returns the height in pixels.
143      * @return the height in pixels of the region of image data
144      * that this <code>SampleModel</code> describes.
145      */

146     final public int getHeight() {
147      return height;
148     }
149
150     /** Returns the total number of bands of image data.
151      * @return the number of bands of image data that this
152      * <code>SampleModel</code> describes.
153      */

154     final public int getNumBands() {
155      return numBands;
156     }
157
158     /** Returns the number of data elements needed to transfer a pixel
159      * via the getDataElements and setDataElements methods. When pixels
160      * are transferred via these methods, they may be transferred in a
161      * packed or unpacked format, depending on the implementation of the
162      * SampleModel. Using these methods, pixels are transferred as an
163      * array of getNumDataElements() elements of a primitive type given
164      * by getTransferType(). The TransferType may or may not be the same
165      * as the storage DataType.
166      * @return the number of data elements.
167      * @see #getDataElements(int, int, Object, DataBuffer)
168      * @see #getDataElements(int, int, int, int, Object, DataBuffer)
169      * @see #setDataElements(int, int, Object, DataBuffer)
170      * @see #setDataElements(int, int, int, int, Object, DataBuffer)
171      * @see #getTransferType
172      */

173     public abstract int getNumDataElements();
174     
175     /** Returns the data type of the DataBuffer storing the pixel data.
176      * @return the data type.
177      */

178     final public int getDataType() {
179     return dataType;
180     }
181
182     /** Returns the TransferType used to transfer pixels via the
183      * getDataElements and setDataElements methods. When pixels
184      * are transferred via these methods, they may be transferred in a
185      * packed or unpacked format, depending on the implementation of the
186      * SampleModel. Using these methods, pixels are transferred as an
187      * array of getNumDataElements() elements of a primitive type given
188      * by getTransferType(). The TransferType may or may not be the same
189      * as the storage DataType. The TransferType will be one of the types
190      * defined in DataBuffer.
191      * @return the transfer type.
192      * @see #getDataElements(int, int, Object, DataBuffer)
193      * @see #getDataElements(int, int, int, int, Object, DataBuffer)
194      * @see #setDataElements(int, int, Object, DataBuffer)
195      * @see #setDataElements(int, int, int, int, Object, DataBuffer)
196      * @see #getNumDataElements
197      * @see java.awt.image.DataBuffer
198      */

199     public int getTransferType() {
200         return dataType;
201     }
202
203     /**
204      * Returns the samples for a specified pixel in an int array,
205      * one sample per array element.
206      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
207      * not in bounds.
208      * @param x,&nbsp;y The coordinates of the pixel location
209      * @param iArray If non-null, returns the samples in this array
210      * @param data The DataBuffer containing the image data
211      * @return the samples for the specified pixel.
212      * @see #setPixel(int, int, int[], DataBuffer)
213      *
214      * @throws NullPointerException if data is null.
215      * @throws ArrayIndexOutOfBoundsException if the coordinates are
216      * not in bounds, or if iArray is too small to hold the output.
217      */

218     public int[] getPixel(int x, int y, int iArray[], DataBuffer JavaDoc data) {
219
220     int pixels[];
221
222     if (iArray != null)
223         pixels = iArray;
224     else
225         pixels = new int[numBands];
226
227     for (int i=0; i<numBands; i++) {
228         pixels[i] = getSample(x, y, i, data);
229     }
230
231     return pixels;
232     }
233
234     /**
235      * Returns data for a single pixel in a primitive array of type
236      * TransferType. For image data supported by the Java 2D API, this
237      * will be one of DataBuffer.TYPE_BYTE, DataBuffer.TYPE_USHORT,
238      * DataBuffer.TYPE_INT, DataBuffer.TYPE_SHORT, DataBuffer.TYPE_FLOAT,
239      * or DataBuffer.TYPE_DOUBLE. Data may be returned in a packed format,
240      * thus increasing efficiency for data transfers. Generally, obj
241      * should be passed in as null, so that the Object will be created
242      * automatically and will be of the right primitive data type.
243      * <p>
244      * The following code illustrates transferring data for one pixel from
245      * DataBuffer <code>db1</code>, whose storage layout is described by
246      * SampleModel <code>sm1</code>, to DataBuffer <code>db2</code>, whose
247      * storage layout is described by SampleModel <code>sm2</code>.
248      * The transfer will generally be more efficient than using
249      * getPixel/setPixel.
250      * <pre>
251      * SampleModel sm1, sm2;
252      * DataBuffer db1, db2;
253      * sm2.setDataElements(x, y, sm1.getDataElements(x, y, null, db1), db2);
254      * </pre>
255      * Using getDataElements/setDataElements to transfer between two
256      * DataBuffer/SampleModel pairs is legitimate if the SampleModels have
257      * the same number of bands, corresponding bands have the same number of
258      * bits per sample, and the TransferTypes are the same.
259      * <p>
260      * If obj is non-null, it should be a primitive array of type TransferType.
261      * Otherwise, a ClassCastException is thrown. An
262      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
263      * not in bounds, or if obj is non-null and is not large enough to hold
264      * the pixel data.
265      * @param x The X coordinate of the pixel location.
266      * @param y The Y coordinate of the pixel location.
267      * @param obj If non-null, a primitive array in which to return
268      * the pixel data.
269      * @param data The DataBuffer containing the image data.
270      * @return the data elements for the specified pixel.
271      * @see #getNumDataElements
272      * @see #getTransferType
273      * @see java.awt.image.DataBuffer
274      * @see #setDataElements(int, int, Object, DataBuffer)
275      *
276      * @throws NullPointerException if data is null.
277      * @throws ArrayIndexOutOfBoundsException if the coordinates are
278      * not in bounds, or if obj is too small to hold the output.
279      */

280     public abstract Object JavaDoc getDataElements(int x, int y,
281                                            Object JavaDoc obj, DataBuffer JavaDoc data);
282
283     /**
284      * Returns the pixel data for the specified rectangle of pixels in a
285      * primitive array of type TransferType.
286      * For image data supported by the Java 2D API, this
287      * will be one of DataBuffer.TYPE_BYTE, DataBuffer.TYPE_USHORT,
288      * DataBuffer.TYPE_INT, DataBuffer.TYPE_SHORT, DataBuffer.TYPE_FLOAT,
289      * or DataBuffer.TYPE_DOUBLE. Data may be returned in a packed format,
290      * thus increasing efficiency for data transfers. Generally, obj
291      * should be passed in as null, so that the Object will be created
292      * automatically and will be of the right primitive data type.
293      * <p>
294      * The following code illustrates transferring data for a rectangular
295      * region of pixels from
296      * DataBuffer <code>db1</code>, whose storage layout is described by
297      * SampleModel <code>sm1</code>, to DataBuffer <code>db2</code>, whose
298      * storage layout is described by SampleModel <code>sm2</code>.
299      * The transfer will generally be more efficient than using
300      * getPixels/setPixels.
301      * <pre>
302      * SampleModel sm1, sm2;
303      * DataBuffer db1, db2;
304      * sm2.setDataElements(x, y, w, h, sm1.getDataElements(x, y, w,
305      * h, null, db1), db2);
306      * </pre>
307      * Using getDataElements/setDataElements to transfer between two
308      * DataBuffer/SampleModel pairs is legitimate if the SampleModels have
309      * the same number of bands, corresponding bands have the same number of
310      * bits per sample, and the TransferTypes are the same.
311      * <p>
312      * If obj is non-null, it should be a primitive array of type TransferType.
313      * Otherwise, a ClassCastException is thrown. An
314      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
315      * not in bounds, or if obj is non-null and is not large enough to hold
316      * the pixel data.
317      * @param x The minimum X coordinate of the pixel rectangle.
318      * @param y The minimum Y coordinate of the pixel rectangle.
319      * @param w The width of the pixel rectangle.
320      * @param h The height of the pixel rectangle.
321      * @param obj If non-null, a primitive array in which to return
322      * the pixel data.
323      * @param data The DataBuffer containing the image data.
324      * @return the data elements for the specified region of pixels.
325      * @see #getNumDataElements
326      * @see #getTransferType
327      * @see #setDataElements(int, int, int, int, Object, DataBuffer)
328      * @see java.awt.image.DataBuffer
329      *
330      * @throws NullPointerException if data is null.
331      * @throws ArrayIndexOutOfBoundsException if the coordinates are
332      * not in bounds, or if obj is too small to hold the output.
333      */

334     public Object JavaDoc getDataElements(int x, int y, int w, int h,
335                                   Object JavaDoc obj, DataBuffer JavaDoc data) {
336
337     int type = getTransferType();
338     int numDataElems = getNumDataElements();
339     int cnt = 0;
340     Object JavaDoc o = null;
341
342     switch(type) {
343
344     case DataBuffer.TYPE_BYTE:
345
346         byte[] btemp;
347         byte[] bdata;
348
349         if (obj == null)
350         bdata = new byte[numDataElems*w*h];
351         else
352         bdata = (byte[])obj;
353
354         for (int i=y; i<y+h; i++) {
355         for (int j=x; j<x+w; j++) {
356             o = getDataElements(j, i, o, data);
357             btemp = (byte[])o;
358             for (int k=0; k<numDataElems; k++) {
359             bdata[cnt++] = btemp[k];
360             }
361         }
362         }
363         obj = (Object JavaDoc)bdata;
364         break;
365
366     case DataBuffer.TYPE_USHORT:
367     case DataBuffer.TYPE_SHORT:
368
369         short[] sdata;
370         short[] stemp;
371
372         if (obj == null)
373         sdata = new short[numDataElems*w*h];
374         else
375         sdata = (short[])obj;
376
377         for (int i=y; i<y+h; i++) {
378         for (int j=x; j<x+w; j++) {
379             o = getDataElements(j, i, o, data);
380             stemp = (short[])o;
381             for (int k=0; k<numDataElems; k++) {
382             sdata[cnt++] = stemp[k];
383             }
384         }
385         }
386
387         obj = (Object JavaDoc)sdata;
388         break;
389
390     case DataBuffer.TYPE_INT:
391
392         int[] idata;
393         int[] itemp;
394
395         if (obj == null)
396         idata = new int[numDataElems*w*h];
397         else
398         idata = (int[])obj;
399
400         for (int i=y; i<y+h; i++) {
401         for (int j=x; j<x+w; j++) {
402             o = getDataElements(j, i, o, data);
403             itemp = (int[])o;
404             for (int k=0; k<numDataElems; k++) {
405             idata[cnt++] = itemp[k];
406             }
407         }
408         }
409
410         obj = (Object JavaDoc)idata;
411         break;
412
413     case DataBuffer.TYPE_FLOAT:
414
415         float[] fdata;
416         float[] ftemp;
417
418         if (obj == null)
419         fdata = new float[numDataElems*w*h];
420         else
421         fdata = (float[])obj;
422
423         for (int i=y; i<y+h; i++) {
424         for (int j=x; j<x+w; j++) {
425             o = getDataElements(j, i, o, data);
426             ftemp = (float[])o;
427             for (int k=0; k<numDataElems; k++) {
428             fdata[cnt++] = ftemp[k];
429             }
430         }
431         }
432
433         obj = (Object JavaDoc)fdata;
434         break;
435
436     case DataBuffer.TYPE_DOUBLE:
437
438         double[] ddata;
439         double[] dtemp;
440
441         if (obj == null)
442         ddata = new double[numDataElems*w*h];
443         else
444         ddata = (double[])obj;
445
446         for (int i=y; i<y+h; i++) {
447         for (int j=x; j<x+w; j++) {
448             o = getDataElements(j, i, o, data);
449             dtemp = (double[])o;
450             for (int k=0; k<numDataElems; k++) {
451             ddata[cnt++] = dtemp[k];
452             }
453         }
454         }
455
456         obj = (Object JavaDoc)ddata;
457         break;
458     }
459
460     return obj;
461     }
462
463     /**
464      * Sets the data for a single pixel in the specified DataBuffer from a
465      * primitive array of type TransferType. For image data supported by
466      * the Java 2D API, this will be one of DataBuffer.TYPE_BYTE,
467      * DataBuffer.TYPE_USHORT, DataBuffer.TYPE_INT, DataBuffer.TYPE_SHORT,
468      * DataBuffer.TYPE_FLOAT, or DataBuffer.TYPE_DOUBLE. Data in the array
469      * may be in a packed format, thus increasing efficiency for data
470      * transfers.
471      * <p>
472      * The following code illustrates transferring data for one pixel from
473      * DataBuffer <code>db1</code>, whose storage layout is described by
474      * SampleModel <code>sm1</code>, to DataBuffer <code>db2</code>, whose
475      * storage layout is described by SampleModel <code>sm2</code>.
476      * The transfer will generally be more efficient than using
477      * getPixel/setPixel.
478      * <pre>
479      * SampleModel sm1, sm2;
480      * DataBuffer db1, db2;
481      * sm2.setDataElements(x, y, sm1.getDataElements(x, y, null, db1),
482      * db2);
483      * </pre>
484      * Using getDataElements/setDataElements to transfer between two
485      * DataBuffer/SampleModel pairs is legitimate if the SampleModels have
486      * the same number of bands, corresponding bands have the same number of
487      * bits per sample, and the TransferTypes are the same.
488      * <p>
489      * obj must be a primitive array of type TransferType. Otherwise,
490      * a ClassCastException is thrown. An
491      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
492      * not in bounds, or if obj is not large enough to hold the pixel data.
493      * @param x The X coordinate of the pixel location.
494      * @param y The Y coordinate of the pixel location.
495      * @param obj A primitive array containing pixel data.
496      * @param data The DataBuffer containing the image data.
497      * @see #getNumDataElements
498      * @see #getTransferType
499      * @see #getDataElements(int, int, Object, DataBuffer)
500      * @see java.awt.image.DataBuffer
501      *
502      * @throws NullPointerException if data is null.
503      * @throws ArrayIndexOutOfBoundsException if the coordinates are
504      * not in bounds, or if obj is too small to hold the input.
505      */

506     public abstract void setDataElements(int x, int y,
507                                          Object JavaDoc obj, DataBuffer JavaDoc data);
508
509     /**
510      * Sets the data for a rectangle of pixels in the specified DataBuffer
511      * from a primitive array of type TransferType. For image data supported
512      * by the Java 2D API, this will be one of DataBuffer.TYPE_BYTE,
513      * DataBuffer.TYPE_USHORT, DataBuffer.TYPE_INT, DataBuffer.TYPE_SHORT,
514      * DataBuffer.TYPE_FLOAT, or DataBuffer.TYPE_DOUBLE. Data in the array
515      * may be in a packed format, thus increasing efficiency for data
516      * transfers.
517      * <p>
518      * The following code illustrates transferring data for a rectangular
519      * region of pixels from
520      * DataBuffer <code>db1</code>, whose storage layout is described by
521      * SampleModel <code>sm1</code>, to DataBuffer <code>db2</code>, whose
522      * storage layout is described by SampleModel <code>sm2</code>.
523      * The transfer will generally be more efficient than using
524      * getPixels/setPixels.
525      * <pre>
526      * SampleModel sm1, sm2;
527      * DataBuffer db1, db2;
528      * sm2.setDataElements(x, y, w, h, sm1.getDataElements(x, y, w, h,
529      * null, db1), db2);
530      * </pre>
531      * Using getDataElements/setDataElements to transfer between two
532      * DataBuffer/SampleModel pairs is legitimate if the SampleModels have
533      * the same number of bands, corresponding bands have the same number of
534      * bits per sample, and the TransferTypes are the same.
535      * <p>
536      * obj must be a primitive array of type TransferType. Otherwise,
537      * a ClassCastException is thrown. An
538      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
539      * not in bounds, or if obj is not large enough to hold the pixel data.
540      * @param x The minimum X coordinate of the pixel rectangle.
541      * @param y The minimum Y coordinate of the pixel rectangle.
542      * @param w The width of the pixel rectangle.
543      * @param h The height of the pixel rectangle.
544      * @param obj A primitive array containing pixel data.
545      * @param data The DataBuffer containing the image data.
546      * @see #getNumDataElements
547      * @see #getTransferType
548      * @see #getDataElements(int, int, int, int, Object, DataBuffer)
549      * @see java.awt.image.DataBuffer
550      *
551      * @throws NullPointerException if data is null.
552      * @throws ArrayIndexOutOfBoundsException if the coordinates are
553      * not in bounds, or if obj is too small to hold the input.
554      */

555     public void setDataElements(int x, int y, int w, int h,
556                                 Object JavaDoc obj, DataBuffer JavaDoc data) {
557
558     int cnt = 0;
559     Object JavaDoc o = null;
560     int type = getTransferType();
561     int numDataElems = getNumDataElements();
562
563     switch(type) {
564
565     case DataBuffer.TYPE_BYTE:
566
567         byte[] barray = (byte[])obj;
568         byte[] btemp = new byte[numDataElems];
569
570         for (int i=y; i<y+h; i++) {
571         for (int j=x; j<x+w; j++) {
572             for (int k=0; k<numDataElems; k++) {
573             btemp[k] = barray[cnt++];
574             }
575
576             setDataElements(j, i, btemp, data);
577         }
578         }
579         break;
580
581     case DataBuffer.TYPE_USHORT:
582     case DataBuffer.TYPE_SHORT:
583
584         short[] sarray = (short[])obj;
585         short[] stemp = new short[numDataElems];
586
587         for (int i=y; i<y+h; i++) {
588         for (int j=x; j<x+w; j++) {
589             for (int k=0; k<numDataElems; k++) {
590             stemp[k] = sarray[cnt++];
591             }
592
593             setDataElements(j, i, stemp, data);
594         }
595         }
596         break;
597
598     case DataBuffer.TYPE_INT:
599
600         int[] iArray = (int[])obj;
601         int[] itemp = new int[numDataElems];
602
603         for (int i=y; i<y+h; i++) {
604         for (int j=x; j<x+w; j++) {
605             for (int k=0; k<numDataElems; k++) {
606             itemp[k] = iArray[cnt++];
607             }
608
609             setDataElements(j, i, itemp, data);
610         }
611         }
612         break;
613
614     case DataBuffer.TYPE_FLOAT:
615
616         float[] fArray = (float[])obj;
617         float[] ftemp = new float[numDataElems];
618
619         for (int i=y; i<y+h; i++) {
620         for (int j=x; j<x+w; j++) {
621             for (int k=0; k<numDataElems; k++) {
622             ftemp[k] = fArray[cnt++];
623             }
624
625             setDataElements(j, i, ftemp, data);
626         }
627         }
628         break;
629
630     case DataBuffer.TYPE_DOUBLE:
631
632         double[] dArray = (double[])obj;
633         double[] dtemp = new double[numDataElems];
634
635         for (int i=y; i<y+h; i++) {
636         for (int j=x; j<x+w; j++) {
637             for (int k=0; k<numDataElems; k++) {
638             dtemp[k] = dArray[cnt++];
639             }
640
641             setDataElements(j, i, dtemp, data);
642         }
643         }
644         break;
645     }
646
647     }
648
649     /**
650      * Returns the samples for the specified pixel in an array of float.
651      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
652      * not in bounds.
653      * @param x The X coordinate of the pixel location.
654      * @param y The Y coordinate of the pixel location.
655      * @param fArray If non-null, returns the samples in this array.
656      * @param data The DataBuffer containing the image data.
657      * @return the samples for the specified pixel.
658      * @see #setPixel(int, int, float[], DataBuffer)
659      *
660      * @throws NullPointerException if data is null.
661      * @throws ArrayIndexOutOfBoundsException if the coordinates are
662      * not in bounds, or if fArray is too small to hold the output.
663      */

664     public float[] getPixel(int x, int y, float fArray[],
665                 DataBuffer JavaDoc data) {
666
667     float pixels[];
668
669     if (fArray != null)
670         pixels = fArray;
671     else
672         pixels = new float[numBands];
673
674     for (int i=0; i<numBands; i++)
675         pixels[i] = getSampleFloat(x, y, i, data);
676
677     return pixels;
678     }
679
680     /**
681      * Returns the samples for the specified pixel in an array of double.
682      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
683      * not in bounds.
684      * @param x The X coordinate of the pixel location.
685      * @param y The Y coordinate of the pixel location.
686      * @param dArray If non-null, returns the samples in this array.
687      * @param data The DataBuffer containing the image data.
688      * @return the samples for the specified pixel.
689      * @see #setPixel(int, int, double[], DataBuffer)
690      *
691      * @throws NullPointerException if data is null.
692      * @throws ArrayIndexOutOfBoundsException if the coordinates are
693      * not in bounds, or if dArray is too small to hold the output.
694      */

695     public double[] getPixel(int x, int y, double dArray[],
696                  DataBuffer JavaDoc data) {
697
698     double pixels[];
699
700     if(dArray != null)
701         pixels = dArray;
702     else
703         pixels = new double[numBands];
704
705     for (int i=0; i<numBands; i++)
706         pixels[i] = getSampleDouble(x, y, i, data);
707
708     return pixels;
709     }
710
711     /**
712      * Returns all samples for a rectangle of pixels in an
713      * int array, one sample per array element.
714      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
715      * not in bounds.
716      * @param x The X coordinate of the upper left pixel location.
717      * @param y The Y coordinate of the upper left pixel location.
718      * @param w The width of the pixel rectangle.
719      * @param h The height of the pixel rectangle.
720      * @param iArray If non-null, returns the samples in this array.
721      * @param data The DataBuffer containing the image data.
722      * @return the samples for the specified region of pixels.
723      * @see #setPixels(int, int, int, int, int[], DataBuffer)
724      *
725      * @throws NullPointerException if data is null.
726      * @throws ArrayIndexOutOfBoundsException if the coordinates are
727      * not in bounds, or if iArray is too small to hold the output.
728      */

729     public int[] getPixels(int x, int y, int w, int h,
730                            int iArray[], DataBuffer JavaDoc data) {
731
732     int pixels[];
733     int Offset=0;
734
735     if (iArray != null)
736         pixels = iArray;
737     else
738         pixels = new int[numBands * w * h];
739
740     for (int i=y; i<(h+y); i++) {
741         for (int j=x; j<(w+x); j++) {
742         for(int k=0; k<numBands; k++) {
743             pixels[Offset++] = getSample(j, i, k, data);
744         }
745         }
746     }
747
748     return pixels;
749     }
750
751     /**
752      * Returns all samples for a rectangle of pixels in a float
753      * array, one sample per array element.
754      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
755      * not in bounds.
756      * @param x The X coordinate of the upper left pixel location.
757      * @param y The Y coordinate of the upper left pixel location.
758      * @param w The width of the pixel rectangle.
759      * @param h The height of the pixel rectangle.
760      * @param fArray If non-null, returns the samples in this array.
761      * @param data The DataBuffer containing the image data.
762      * @return the samples for the specified region of pixels.
763      * @see #setPixels(int, int, int, int, float[], DataBuffer)
764      *
765      * @throws NullPointerException if data is null.
766      * @throws ArrayIndexOutOfBoundsException if the coordinates are
767      * not in bounds, or if fArray is too small to hold the output.
768      */

769     public float[] getPixels(int x, int y, int w, int h,
770                              float fArray[], DataBuffer JavaDoc data) {
771
772     float pixels[];
773     int Offset = 0;
774
775     if (fArray != null)
776         pixels = fArray;
777     else
778         pixels = new float[numBands * w * h];
779
780     for (int i=y; i<(h+y); i++) {
781         for(int j=x; j<(w+x); j++) {
782         for(int k=0; k<numBands; k++) {
783             pixels[Offset++] = getSampleFloat(j, i, k, data);
784         }
785         }
786     }
787
788     return pixels;
789     }
790
791     /**
792      * Returns all samples for a rectangle of pixels in a double
793      * array, one sample per array element.
794      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
795      * not in bounds.
796      * @param x The X coordinate of the upper left pixel location.
797      * @param y The Y coordinate of the upper left pixel location.
798      * @param w The width of the pixel rectangle.
799      * @param h The height of the pixel rectangle.
800      * @param dArray If non-null, returns the samples in this array.
801      * @param data The DataBuffer containing the image data.
802      * @return the samples for the specified region of pixels.
803      * @see #setPixels(int, int, int, int, double[], DataBuffer)
804      *
805      * @throws NullPointerException if data is null.
806      * @throws ArrayIndexOutOfBoundsException if the coordinates are
807      * not in bounds, or if dArray is too small to hold the output.
808      */

809     public double[] getPixels(int x, int y, int w, int h,
810                               double dArray[], DataBuffer JavaDoc data) {
811     double pixels[];
812     int Offset = 0;
813
814     if (dArray != null)
815         pixels = dArray;
816     else
817         pixels = new double[numBands * w * h];
818
819         // Fix 4217412
820
for (int i=y; i<(h+y); i++) {
821         for (int j=x; j<(w+x); j++) {
822         for (int k=0; k<numBands; k++) {
823             pixels[Offset++] = getSampleDouble(j, i, k, data);
824         }
825         }
826     }
827
828     return pixels;
829     }
830
831
832     /**
833      * Returns the sample in a specified band for the pixel located
834      * at (x,y) as an int.
835      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
836      * not in bounds.
837      * @param x The X coordinate of the pixel location.
838      * @param y The Y coordinate of the pixel location.
839      * @param b The band to return.
840      * @param data The DataBuffer containing the image data.
841      * @return the sample in a specified band for the specified pixel.
842      * @see #setSample(int, int, int, int, DataBuffer)
843      *
844      * @throws NullPointerException if data is null.
845      * @throws ArrayIndexOutOfBoundsException if the coordinates or
846      * the band index are not in bounds.
847      */

848     public abstract int getSample(int x, int y, int b, DataBuffer JavaDoc data);
849
850
851     /**
852      * Returns the sample in a specified band
853      * for the pixel located at (x,y) as a float.
854      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
855      * not in bounds.
856      * @param x The X coordinate of the pixel location.
857      * @param y The Y coordinate of the pixel location.
858      * @param b The band to return.
859      * @param data The DataBuffer containing the image data.
860      * @return the sample in a specified band for the specified pixel.
861      *
862      * @throws NullPointerException if data is null.
863      * @throws ArrayIndexOutOfBoundsException if the coordinates or
864      * the band index are not in bounds.
865      */

866     public float getSampleFloat(int x, int y, int b, DataBuffer JavaDoc data) {
867
868     float sample;
869     sample = (float) getSample(x, y, b, data);
870     return sample;
871     }
872
873     /**
874      * Returns the sample in a specified band
875      * for a pixel located at (x,y) as a double.
876      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
877      * not in bounds.
878      * @param x The X coordinate of the pixel location.
879      * @param y The Y coordinate of the pixel location.
880      * @param b The band to return.
881      * @param data The DataBuffer containing the image data.
882      * @return the sample in a specified band for the specified pixel.
883      *
884      * @throws NullPointerException if data is null.
885      * @throws ArrayIndexOutOfBoundsException if the coordinates or
886      * the band index are not in bounds.
887      */

888     public double getSampleDouble(int x, int y, int b, DataBuffer JavaDoc data) {
889
890     double sample;
891
892     sample = (double) getSample(x, y, b, data);
893     return sample;
894     }
895
896     /**
897      * Returns the samples for a specified band for the specified rectangle
898      * of pixels in an int array, one sample per array element.
899      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
900      * not in bounds.
901      * @param x The X coordinate of the upper left pixel location.
902      * @param y The Y coordinate of the upper left pixel location.
903      * @param w The width of the pixel rectangle.
904      * @param h The height of the pixel rectangle.
905      * @param b The band to return.
906      * @param iArray If non-null, returns the samples in this array.
907      * @param data The DataBuffer containing the image data.
908      * @return the samples for the specified band for the specified region
909      * of pixels.
910      * @see #setSamples(int, int, int, int, int, int[], DataBuffer)
911      *
912      * @throws NullPointerException if data is null.
913      * @throws ArrayIndexOutOfBoundsException if the coordinates or
914      * the band index are not in bounds, or if iArray is too small to
915      * hold the output.
916      */

917     public int[] getSamples(int x, int y, int w, int h, int b,
918                             int iArray[], DataBuffer JavaDoc data) {
919     int pixels[];
920     int Offset=0;
921
922     if (iArray != null)
923         pixels = iArray;
924     else
925         pixels = new int[w * h];
926
927     for(int i=y; i<(h+y); i++) {
928         for (int j=x; j<(w+x); j++) {
929         pixels[Offset++] = getSample(j, i, b, data);
930         }
931     }
932
933     return pixels;
934     }
935
936     /**
937      * Returns the samples for a specified band for the specified rectangle
938      * of pixels in a float array, one sample per array element.
939      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
940      * not in bounds.
941      * @param x The X coordinate of the upper left pixel location.
942      * @param y The Y coordinate of the upper left pixel location.
943      * @param w The width of the pixel rectangle.
944      * @param h The height of the pixel rectangle.
945      * @param b The band to return.
946      * @param fArray If non-null, returns the samples in this array.
947      * @param data The DataBuffer containing the image data.
948      * @return the samples for the specified band for the specified region
949      * of pixels.
950      * @see #setSamples(int, int, int, int, int, float[], DataBuffer)
951      *
952      * @throws NullPointerException if data is null.
953      * @throws ArrayIndexOutOfBoundsException if the coordinates or
954      * the band index are not in bounds, or if fArray is too small to
955      * hold the output.
956      */

957     public float[] getSamples(int x, int y, int w, int h,
958                               int b, float fArray[],
959                               DataBuffer JavaDoc data) {
960     float pixels[];
961     int Offset=0;
962
963     if (fArray != null)
964         pixels = fArray;
965     else
966         pixels = new float[w * h];
967
968     for (int i=y; i<(h+y); i++) {
969         for (int j=x; j<(w+x); j++) {
970         pixels[Offset++] = getSampleFloat(j, i, b, data);
971         }
972     }
973
974     return pixels;
975     }
976
977     /**
978      * Returns the samples for a specified band for a specified rectangle
979      * of pixels in a double array, one sample per array element.
980      * ArrayIndexOutOfBoundsException may be thrown if the coordinates are
981      * not in bounds.
982      * @param x The X coordinate of the upper left pixel location.
983      * @param y The Y coordinate of the upper left pixel location.
984      * @param w The width of the pixel rectangle.
985      * @param h The height of the pixel rectangle.
986      * @param b The band to return.
987      * @param dArray If non-null, returns the samples in this array.
988      * @param data The DataBuffer containing the image data.
989      * @return the samples for the specified band for the specified region
990      * of pixels.
991      * @see #setSamples(int, int, int, int, int, double[], DataBuffer)
992      *
993      * @throws NullPointerException if data is null.
994      * @throws ArrayIndexOutOfBoundsException if the coordinates or
995      * the band index are not in bounds, or if dArray is too small to
996      * hold the output.
997      */

998     public double[] getSamples(int x,