diff options
Diffstat (limited to 'awt/java/awt/image/IndexColorModel.java')
-rw-r--r-- | awt/java/awt/image/IndexColorModel.java | 1080 |
1 files changed, 1080 insertions, 0 deletions
diff --git a/awt/java/awt/image/IndexColorModel.java b/awt/java/awt/image/IndexColorModel.java new file mode 100644 index 0000000..0b06acd --- /dev/null +++ b/awt/java/awt/image/IndexColorModel.java @@ -0,0 +1,1080 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/** + * @author Igor V. Stolyarov + * @version $Revision$ + */ + +package java.awt.image; + +import java.awt.Transparency; +import java.awt.color.ColorSpace; +import java.math.BigInteger; + +import org.apache.harmony.awt.internal.nls.Messages; + +/** + * The Class IndexColorModel represents a color model in which the color values + * of the pixels are read from a palette. + * + * @since Android 1.0 + */ +public class IndexColorModel extends ColorModel { + + /** + * The color map. + */ + private int colorMap[]; // Color Map + + /** + * The map size. + */ + private int mapSize; // Color Map size + + /** + * The transparent index. + */ + private int transparentIndex; // Index of fully transparent pixel + + /** + * The gray palette. + */ + private boolean grayPalette; // Color Model has Color Map with Gray Pallete + + /** + * The valid bits. + */ + private BigInteger validBits; // Specify valid Color Map values + + /** + * The Constant CACHESIZE. + */ + private static final int CACHESIZE = 20; // Cache size. Cache used for + + // improving performace of selection + // nearest color in Color Map + + /** + * The cachetable. + */ + private final int cachetable[] = new int[CACHESIZE * 2]; // Cache table - + + // used for + + // storing RGB values and that appropriate indices + // in the Color Map + + /** + * The next insert idx. + */ + private int nextInsertIdx = 0; // Next index for insertion into Cache table + + /** + * The total inserted. + */ + private int totalInserted = 0; // Number of inserted values into Cache table + + /** + * Instantiates a new index color model. + * + * @param bits + * the array of component masks. + * @param size + * the size of the color map. + * @param cmap + * the array that gives the color mapping. + * @param start + * the start index of the color mapping data within the cmap + * array. + * @param transferType + * the transfer type (primitive java type to use for the + * components). + * @param validBits + * a list of which bits represent valid colormap values, or null + * if all are valid. + * @throws IllegalArgumentException + * if the size of the color map is less than one. + */ + public IndexColorModel(int bits, int size, int cmap[], int start, int transferType, + BigInteger validBits) { + + super(bits, IndexColorModel.createBits(true), ColorSpace.getInstance(ColorSpace.CS_sRGB), + true, false, Transparency.OPAQUE, validateTransferType(transferType)); + + if (size < 1) { + // awt.264=Size of the color map is less than 1 + throw new IllegalArgumentException(Messages.getString("awt.264")); //$NON-NLS-1$ + } + + mapSize = size; + colorMap = new int[mapSize]; + transparentIndex = -1; + + if (validBits != null) { + for (int i = 0; i < mapSize; i++) { + if (!validBits.testBit(i)) { + this.validBits = validBits; + } + break; + } + } + + transparency = Transparency.OPAQUE; + int alphaMask = 0xff000000; + int alpha = 0; + + for (int i = 0; i < mapSize; i++, start++) { + colorMap[i] = cmap[start]; + alpha = cmap[start] & alphaMask; + + if (alpha == alphaMask) { + continue; + } + if (alpha == 0) { + if (transparentIndex < 0) { + transparentIndex = i; + } + if (transparency == Transparency.OPAQUE) { + transparency = Transparency.BITMASK; + } + } else if (alpha != alphaMask && transparency != Transparency.TRANSLUCENT) { + transparency = Transparency.TRANSLUCENT; + } + + } + checkPalette(); + + } + + /** + * Instantiates a new index color model. + * + * @param bits + * the array of component masks. + * @param size + * the size of the color map. + * @param cmap + * the array that gives the color mapping. + * @param start + * the start index of the color mapping data within the cmap + * array. + * @param hasalpha + * whether this color model uses alpha. + * @param trans + * the transparency supported, @see java.awt.Transparency. + * @param transferType + * the transfer type (primitive java type to use for the + * components). + * @throws IllegalArgumentException + * if the size of the color map is less than one. + */ + public IndexColorModel(int bits, int size, int cmap[], int start, boolean hasalpha, int trans, + int transferType) { + + super(bits, IndexColorModel.createBits(hasalpha || (trans >= 0)), ColorSpace + .getInstance(ColorSpace.CS_sRGB), (hasalpha || (trans >= 0)), false, + Transparency.OPAQUE, validateTransferType(transferType)); + + if (size < 1) { + // awt.264=Size of the color map is less than 1 + throw new IllegalArgumentException(Messages.getString("awt.264")); //$NON-NLS-1$ + } + + mapSize = size; + colorMap = new int[mapSize]; + if (trans >= 0 && trans < mapSize) { + transparentIndex = trans; + transparency = Transparency.BITMASK; + } else { + transparentIndex = -1; + transparency = Transparency.OPAQUE; + } + + int alphaMask = 0xff000000; + int alpha = 0; + + for (int i = 0; i < mapSize; i++, start++) { + if (transparentIndex == i) { + colorMap[i] = cmap[start] & 0x00ffffff; + continue; + } + if (hasalpha) { + alpha = cmap[start] & alphaMask; + colorMap[i] = cmap[start]; + + if (alpha == alphaMask) { + continue; + } + if (alpha == 0) { + if (trans < 0) { + trans = i; + } + if (transparency == Transparency.OPAQUE) { + transparency = Transparency.BITMASK; + } + } else if (alpha != 0 && transparency != Transparency.TRANSLUCENT) { + transparency = Transparency.TRANSLUCENT; + } + } else { + colorMap[i] = alphaMask | cmap[start]; + } + } + checkPalette(); + + } + + /** + * Instantiates a new index color model by building the color map from + * arrays of red, green, blue, and alpha values. + * + * @param bits + * the array of component masks. + * @param size + * the size of the color map. + * @param r + * the array giving the red components of the entries in the + * color map. + * @param g + * the array giving the green components of the entries in the + * color map. + * @param b + * the array giving the blue components of the entries in the + * color map. + * @param a + * the array giving the alpha components of the entries in the + * color map. + * @throws IllegalArgumentException + * if the size of the color map is less than one. + * @throws ArrayIndexOutOfBoundsException + * if the size of one of the component arrays is less than the + * size of the color map. + */ + public IndexColorModel(int bits, int size, byte r[], byte g[], byte b[], byte a[]) { + + super(bits, IndexColorModel.createBits(true), ColorSpace.getInstance(ColorSpace.CS_sRGB), + true, false, Transparency.OPAQUE, validateTransferType(ColorModel + .getTransferType(bits))); + + createColorMap(size, r, g, b, a, -1); + checkPalette(); + } + + /** + * Instantiates a new index color model by building the color map from + * arrays of red, green, and blue values. + * + * @param bits + * the array of component masks. + * @param size + * the size of the color map. + * @param r + * the array giving the red components of the entries in the + * color map. + * @param g + * the array giving the green components of the entries in the + * color map. + * @param b + * the array giving the blue components of the entries in the + * color map. + * @param trans + * the transparency supported, @see java.awt.Transparency. + * @throws IllegalArgumentException + * if the size of the color map is less than one. + * @throws ArrayIndexOutOfBoundsException + * if the size of one of the component arrays is less than the + * size of the color map. + */ + public IndexColorModel(int bits, int size, byte r[], byte g[], byte b[], int trans) { + + super(bits, IndexColorModel.createBits((trans >= 0)), ColorSpace + .getInstance(ColorSpace.CS_sRGB), (trans >= 0), false, Transparency.OPAQUE, + validateTransferType(ColorModel.getTransferType(bits))); + + createColorMap(size, r, g, b, null, trans); + checkPalette(); + } + + /** + * Instantiates a new index color model by building the color map from + * arrays of red, green, and blue values. + * + * @param bits + * the array of component masks. + * @param size + * the size of the color map. + * @param r + * the array giving the red components of the entries in the + * color map. + * @param g + * the array giving the green components of the entries in the + * color map. + * @param b + * the array giving the blue components of the entries in the + * color map. + * @throws IllegalArgumentException + * if the size of the color map is less than one. + * @throws ArrayIndexOutOfBoundsException + * if the size of one of the component arrays is less than the + * size of the color map. + */ + public IndexColorModel(int bits, int size, byte r[], byte g[], byte b[]) { + super(bits, IndexColorModel.createBits(false), ColorSpace.getInstance(ColorSpace.CS_sRGB), + false, false, Transparency.OPAQUE, validateTransferType(ColorModel + .getTransferType(bits))); + + createColorMap(size, r, g, b, null, -1); + checkPalette(); + } + + /** + * Instantiates a new index color model. + * + * @param bits + * the array of component masks. + * @param size + * the size of the color map. + * @param cmap + * the array that gives the color mapping. + * @param start + * the start index of the color mapping data within the cmap + * array. + * @param hasalpha + * whether this color model uses alpha. + * @param trans + * the transparency supported, @see java.awt.Transparency. + * @throws IllegalArgumentException + * if the size of the color map is less than one. + */ + public IndexColorModel(int bits, int size, byte cmap[], int start, boolean hasalpha, int trans) { + + super(bits, IndexColorModel.createBits(hasalpha || (trans >= 0)), ColorSpace + .getInstance(ColorSpace.CS_sRGB), (hasalpha || (trans >= 0)), false, + Transparency.OPAQUE, validateTransferType(ColorModel.getTransferType(bits))); + + if (size < 1) { + // awt.264=Size of the color map is less than 1 + throw new IllegalArgumentException(Messages.getString("awt.264")); //$NON-NLS-1$ + } + + mapSize = size; + colorMap = new int[mapSize]; + transparentIndex = -1; + + transparency = Transparency.OPAQUE; + int alpha = 0xff000000; + + for (int i = 0; i < mapSize; i++) { + colorMap[i] = (cmap[start++] & 0xff) << 16 | (cmap[start++] & 0xff) << 8 + | (cmap[start++] & 0xff); + if (trans == i) { + if (transparency == Transparency.OPAQUE) { + transparency = Transparency.BITMASK; + } + if (hasalpha) { + start++; + } + continue; + } + if (hasalpha) { + alpha = cmap[start++] & 0xff; + if (alpha == 0) { + if (transparency == Transparency.OPAQUE) { + transparency = Transparency.BITMASK; + if (trans < 0) { + trans = i; + } + } + } else { + if (alpha != 0xff && transparency != Transparency.TRANSLUCENT) { + transparency = Transparency.TRANSLUCENT; + } + } + alpha <<= 24; + } + colorMap[i] |= alpha; + } + + if (trans >= 0 && trans < mapSize) { + transparentIndex = trans; + } + checkPalette(); + + } + + /** + * Instantiates a new index color model. + * + * @param bits + * the array of component masks. + * @param size + * the size of the color map. + * @param cmap + * the array that gives the color mapping. + * @param start + * the start index of the color mapping data within the cmap + * array. + * @param hasalpha + * whether this color model uses alpha. + * @throws IllegalArgumentException + * if the size of the color map is less than one. + */ + public IndexColorModel(int bits, int size, byte cmap[], int start, boolean hasalpha) { + + this(bits, size, cmap, start, hasalpha, -1); + } + + @Override + public Object getDataElements(int[] components, int offset, Object pixel) { + int rgb = (components[offset] << 16) | (components[offset + 1]) << 8 + | components[offset + 2]; + if (hasAlpha) { + rgb |= components[offset + 3] << 24; + } else { + rgb |= 0xff000000; + } + return getDataElements(rgb, pixel); + } + + @Override + public synchronized Object getDataElements(int rgb, Object pixel) { + int red = (rgb >> 16) & 0xff; + int green = (rgb >> 8) & 0xff; + int blue = rgb & 0xff; + int alpha = rgb >>> 24; + int pixIdx = 0; + + for (int i = 0; i < totalInserted; i++) { + int idx = i * 2; + if (rgb == cachetable[idx]) { + return createDataObject(cachetable[idx + 1], pixel); + } + } + + if (!hasAlpha && grayPalette) { + int grey = (red * 77 + green * 150 + blue * 29 + 128) >>> 8; + int minError = 255; + int error = 0; + + for (int i = 0; i < mapSize; i++) { + error = Math.abs((colorMap[i] & 0xff) - grey); + if (error < minError) { + pixIdx = i; + if (error == 0) { + break; + } + minError = error; + } + } + } else if (alpha == 0 && transparentIndex > -1) { + pixIdx = transparentIndex; + } else { + int minAlphaError = 255; + int minError = 195075; // 255^2 + 255^2 + 255^2 + int alphaError; + int error = 0; + + for (int i = 0; i < mapSize; i++) { + int pix = colorMap[i]; + if (rgb == pix) { + pixIdx = i; + break; + } + alphaError = Math.abs(alpha - (pix >>> 24)); + if (alphaError <= minAlphaError) { + minAlphaError = alphaError; + + int buf = ((pix >> 16) & 0xff) - red; + error = buf * buf; + + if (error < minError) { + buf = ((pix >> 8) & 0xff) - green; + error += buf * buf; + + if (error < minError) { + buf = (pix & 0xff) - blue; + error += buf * buf; + + if (error < minError) { + pixIdx = i; + minError = error; + } + } + } + } + } + } + + cachetable[nextInsertIdx] = rgb; + cachetable[nextInsertIdx + 1] = pixIdx; + + nextInsertIdx = (nextInsertIdx + 2) % (CACHESIZE * 2); + if (totalInserted < CACHESIZE) { + totalInserted++; + } + + return createDataObject(pixIdx, pixel); + } + + /** + * Converts an image from indexed to RGB format. + * + * @param raster + * the raster containing the source image. + * @param forceARGB + * whether to use the default RGB color model. + * @return the buffered image. + * @throws IllegalArgumentException + * if the raster is not compatible with this color model. + */ + public BufferedImage convertToIntDiscrete(Raster raster, boolean forceARGB) { + + if (!isCompatibleRaster(raster)) { + // awt.265=The raster argument is not compatible with this + // IndexColorModel + throw new IllegalArgumentException(Messages.getString("awt.265")); //$NON-NLS-1$ + } + + ColorModel model; + if (forceARGB || transparency == Transparency.TRANSLUCENT) { + model = ColorModel.getRGBdefault(); + } else if (transparency == Transparency.BITMASK) { + model = new DirectColorModel(25, 0x00ff0000, 0x0000ff00, 0x000000ff, 0x01000000); + } else { + model = new DirectColorModel(24, 0x00ff0000, 0x0000ff00, 0x000000ff); + } + + int w = raster.getWidth(); + int h = raster.getHeight(); + + WritableRaster distRaster = model.createCompatibleWritableRaster(w, h); + + int minX = raster.getMinX(); + int minY = raster.getMinY(); + + Object obj = null; + int pixels[] = null; + + for (int i = 0; i < h; i++, minY++) { + obj = raster.getDataElements(minX, minY, w, 1, obj); + if (obj instanceof byte[]) { + byte ba[] = (byte[])obj; + if (pixels == null) { + pixels = new int[ba.length]; + } + for (int j = 0; j < ba.length; j++) { + pixels[j] = colorMap[ba[j] & 0xff]; + } + } else if (obj instanceof short[]) { + short sa[] = (short[])obj; + if (pixels == null) { + pixels = new int[sa.length]; + } + for (int j = 0; j < sa.length; j++) { + pixels[j] = colorMap[sa[j] & 0xffff]; + } + } + if (obj instanceof int[]) { + int ia[] = (int[])obj; + if (pixels == null) { + pixels = new int[ia.length]; + } + for (int j = 0; j < ia.length; j++) { + pixels[j] = colorMap[ia[j]]; + } + } + + distRaster.setDataElements(0, i, w, 1, pixels); + } + + return new BufferedImage(model, distRaster, false, null); + } + + /** + * Gets the valid pixels. + * + * @return the valid pixels. + */ + public BigInteger getValidPixels() { + return validBits; + } + + @Override + public String toString() { + // The output format based on 1.5 release behaviour. + // It could be reveled such way: + // BufferedImage bi = new BufferedImage(1, 1, + // BufferedImage.TYPE_BYTE_INDEXED); + // ColorModel cm = bi.getColorModel(); + // System.out.println(cm.toString()); + String str = "IndexColorModel: #pixel_bits = " + pixel_bits + //$NON-NLS-1$ + " numComponents = " + numComponents + " color space = " + cs + //$NON-NLS-1$ //$NON-NLS-2$ + " transparency = "; //$NON-NLS-1$ + + if (transparency == Transparency.OPAQUE) { + str = str + "Transparency.OPAQUE"; //$NON-NLS-1$ + } else if (transparency == Transparency.BITMASK) { + str = str + "Transparency.BITMASK"; //$NON-NLS-1$ + } else { + str = str + "Transparency.TRANSLUCENT"; //$NON-NLS-1$ + } + + str = str + " transIndex = " + transparentIndex + " has alpha = " + //$NON-NLS-1$ //$NON-NLS-2$ + hasAlpha + " isAlphaPre = " + isAlphaPremultiplied; //$NON-NLS-1$ + + return str; + } + + @Override + public int[] getComponents(Object pixel, int components[], int offset) { + int pixIdx = -1; + if (pixel instanceof byte[]) { + byte ba[] = (byte[])pixel; + pixIdx = ba[0] & 0xff; + } else if (pixel instanceof short[]) { + short sa[] = (short[])pixel; + pixIdx = sa[0] & 0xffff; + } else if (pixel instanceof int[]) { + int ia[] = (int[])pixel; + pixIdx = ia[0]; + } else { + // awt.219=This transferType is not supported by this color model + throw new UnsupportedOperationException(Messages.getString("awt.219")); //$NON-NLS-1$ + } + + return getComponents(pixIdx, components, offset); + } + + @Override + public WritableRaster createCompatibleWritableRaster(int w, int h) { + WritableRaster raster; + if (pixel_bits == 1 || pixel_bits == 2 || pixel_bits == 4) { + raster = Raster.createPackedRaster(DataBuffer.TYPE_BYTE, w, h, 1, pixel_bits, null); + } else if (pixel_bits <= 8) { + raster = Raster.createInterleavedRaster(DataBuffer.TYPE_BYTE, w, h, 1, null); + } else if (pixel_bits <= 16) { + raster = Raster.createInterleavedRaster(DataBuffer.TYPE_USHORT, w, h, 1, null); + } else { + // awt.266=The number of bits in a pixel is greater than 16 + throw new UnsupportedOperationException(Messages.getString("awt.266")); //$NON-NLS-1$ + } + + return raster; + } + + @Override + public boolean isCompatibleSampleModel(SampleModel sm) { + if (sm == null) { + return false; + } + + if (!(sm instanceof MultiPixelPackedSampleModel) && !(sm instanceof ComponentSampleModel)) { + return false; + } + + if (sm.getTransferType() != transferType) { + return false; + } + if (sm.getNumBands() != 1) { + return false; + } + + return true; + } + + @Override + public SampleModel createCompatibleSampleModel(int w, int h) { + if (pixel_bits == 1 || pixel_bits == 2 || pixel_bits == 4) { + return new MultiPixelPackedSampleModel(DataBuffer.TYPE_BYTE, w, h, pixel_bits); + } + int bandOffsets[] = new int[1]; + bandOffsets[0] = 0; + return new ComponentSampleModel(transferType, w, h, 1, w, bandOffsets); + + } + + @Override + public boolean isCompatibleRaster(Raster raster) { + int sampleSize = raster.getSampleModel().getSampleSize(0); + return (raster.getTransferType() == transferType && raster.getNumBands() == 1 && (1 << sampleSize) >= mapSize); + } + + @Override + public int getDataElement(int components[], int offset) { + int rgb = (components[offset] << 16) | (components[offset + 1]) << 8 + | components[offset + 2]; + + if (hasAlpha) { + rgb |= components[offset + 3] << 24; + } else { + rgb |= 0xff000000; + } + + int pixel; + + switch (transferType) { + case DataBuffer.TYPE_BYTE: + byte ba[] = (byte[])getDataElements(rgb, null); + pixel = ba[0] & 0xff; + break; + case DataBuffer.TYPE_USHORT: + short sa[] = (short[])getDataElements(rgb, null); + pixel = sa[0] & 0xffff; + break; + default: + // awt.267=The transferType is invalid + throw new UnsupportedOperationException(Messages.getString("awt.267")); //$NON-NLS-1$ + } + + return pixel; + } + + /** + * Gets the color map. + * + * @param rgb + * the destination array where the color map is written. + */ + public final void getRGBs(int rgb[]) { + System.arraycopy(colorMap, 0, rgb, 0, mapSize); + } + + /** + * Gets the red component of the color map. + * + * @param r + * the destination array. + */ + public final void getReds(byte r[]) { + for (int i = 0; i < mapSize; i++) { + r[i] = (byte)(colorMap[i] >> 16); + } + } + + /** + * Gets the green component of the color map. + * + * @param g + * the destination array. + */ + public final void getGreens(byte g[]) { + for (int i = 0; i < mapSize; i++) { + g[i] = (byte)(colorMap[i] >> 8); + } + } + + /** + * Gets the blue component of the color map. + * + * @param b + * the destination array. + */ + public final void getBlues(byte b[]) { + for (int i = 0; i < mapSize; i++) { + b[i] = (byte)colorMap[i]; + } + } + + /** + * Gets the alpha component of the color map. + * + * @param a + * the destination array. + */ + public final void getAlphas(byte a[]) { + for (int i = 0; i < mapSize; i++) { + a[i] = (byte)(colorMap[i] >> 24); + } + } + + @Override + public int[] getComponents(int pixel, int components[], int offset) { + if (components == null) { + components = new int[offset + numComponents]; + } + + components[offset + 0] = getRed(pixel); + components[offset + 1] = getGreen(pixel); + components[offset + 2] = getBlue(pixel); + if (hasAlpha && (components.length - offset) > 3) { + components[offset + 3] = getAlpha(pixel); + } + + return components; + } + + /** + * Checks if the specified pixel is valid for this color model. + * + * @param pixel + * the pixel. + * @return true, if the pixel is valid. + */ + public boolean isValid(int pixel) { + if (validBits == null) { + return (pixel >= 0 && pixel < mapSize); + } + return (pixel < mapSize && validBits.testBit(pixel)); + } + + @Override + public final int getRed(int pixel) { + return (colorMap[pixel] >> 16) & 0xff; + } + + @Override + public final int getRGB(int pixel) { + return colorMap[pixel]; + } + + @Override + public final int getGreen(int pixel) { + return (colorMap[pixel] >> 8) & 0xff; + } + + @Override + public final int getBlue(int pixel) { + return colorMap[pixel] & 0xff; + } + + @Override + public final int getAlpha(int pixel) { + return (colorMap[pixel] >> 24) & 0xff; + } + + @Override + public int[] getComponentSize() { + return bits.clone(); + } + + /** + * Checks if this color model validates pixels. + * + * @return true, if all pixels are valid, otherwise false. + */ + public boolean isValid() { + return (validBits == null); + } + + @Override + public void finalize() { + // TODO: implement + return; + } + + /** + * Gets the index that represents the transparent pixel. + * + * @return the index that represents the transparent pixel. + */ + public final int getTransparentPixel() { + return transparentIndex; + } + + @Override + public int getTransparency() { + return transparency; + } + + /** + * Gets the size of the color map. + * + * @return the map size. + */ + public final int getMapSize() { + return mapSize; + } + + /** + * Creates the color map. + * + * @param size + * the size. + * @param r + * the r. + * @param g + * the g. + * @param b + * the b. + * @param a + * the a. + * @param trans + * the trans. + */ + private void createColorMap(int size, byte r[], byte g[], byte b[], byte a[], int trans) { + if (size < 1) { + // awt.264=Size of the color map is less than 1 + throw new IllegalArgumentException(Messages.getString("awt.264")); //$NON-NLS-1$ + } + + mapSize = size; + colorMap = new int[mapSize]; + if (trans >= 0 && trans < mapSize) { + transparency = Transparency.BITMASK; + transparentIndex = trans; + } else { + transparency = Transparency.OPAQUE; + transparentIndex = -1; + } + int alpha = 0; + + for (int i = 0; i < mapSize; i++) { + colorMap[i] = ((r[i] & 0xff) << 16) | ((g[i] & 0xff) << 8) | (b[i] & 0xff); + + if (trans == i) { + continue; + } + + if (a == null) { + colorMap[i] |= 0xff000000; + } else { + alpha = a[i] & 0xff; + if (alpha == 0xff) { + colorMap[i] |= 0xff000000; + } else if (alpha == 0) { + if (transparency == Transparency.OPAQUE) { + transparency = Transparency.BITMASK; + } + if (transparentIndex < 0) { + transparentIndex = i; + } + } else { + colorMap[i] |= (a[i] & 0xff) << 24; + if (transparency != Transparency.TRANSLUCENT) { + transparency = Transparency.TRANSLUCENT; + } + } + } + + } + + } + + /** + * This method checking, if Color Map has Gray palette. + */ + private void checkPalette() { + grayPalette = false; + if (transparency > Transparency.OPAQUE) { + return; + } + int rgb = 0; + + for (int i = 0; i < mapSize; i++) { + rgb = colorMap[i]; + if (((rgb >> 16) & 0xff) != ((rgb >> 8) & 0xff) || ((rgb >> 8) & 0xff) != (rgb & 0xff)) { + return; + } + } + grayPalette = true; + } + + /** + * Construction an array pixel representation. + * + * @param colorMapIdx + * the index into Color Map. + * @param pixel + * the pixel + * @return the pixel representation array. + */ + private Object createDataObject(int colorMapIdx, Object pixel) { + if (pixel == null) { + switch (transferType) { + case DataBuffer.TYPE_BYTE: + byte[] ba = new byte[1]; + ba[0] = (byte)colorMapIdx; + pixel = ba; + break; + case DataBuffer.TYPE_USHORT: + short[] sa = new short[1]; + sa[0] = (short)colorMapIdx; + pixel = sa; + break; + default: + // awt.267=The transferType is invalid + throw new UnsupportedOperationException(Messages.getString("awt.267")); //$NON-NLS-1$ + } + } else if (pixel instanceof byte[] && transferType == DataBuffer.TYPE_BYTE) { + byte ba[] = (byte[])pixel; + ba[0] = (byte)colorMapIdx; + pixel = ba; + } else if (pixel instanceof short[] && transferType == DataBuffer.TYPE_USHORT) { + short[] sa = (short[])pixel; + sa[0] = (short)colorMapIdx; + pixel = sa; + } else if (pixel instanceof int[]) { + int ia[] = (int[])pixel; + ia[0] = colorMapIdx; + pixel = ia; + } else { + // awt.268=The pixel is not a primitive array of type transferType + throw new ClassCastException(Messages.getString("awt.268")); //$NON-NLS-1$ + } + return pixel; + } + + /** + * Creates the bits. + * + * @param hasAlpha + * the has alpha. + * @return the int[]. + */ + private static int[] createBits(boolean hasAlpha) { + + int numChannels; + if (hasAlpha) { + numChannels = 4; + } else { + numChannels = 3; + } + + int bits[] = new int[numChannels]; + for (int i = 0; i < numChannels; i++) { + bits[i] = 8; + } + + return bits; + + } + + /** + * Validate transfer type. + * + * @param transferType + * the transfer type. + * @return the int. + */ + private static int validateTransferType(int transferType) { + if (transferType != DataBuffer.TYPE_BYTE && transferType != DataBuffer.TYPE_USHORT) { + // awt.269=The transferType is not one of DataBuffer.TYPE_BYTE or + // DataBuffer.TYPE_USHORT + throw new IllegalArgumentException(Messages.getString("awt.269")); //$NON-NLS-1$ + } + return transferType; + } + + /** + * Checks if is gray palette. + * + * @return true, if is gray palette. + */ + boolean isGrayPallete() { + return grayPalette; + } + +} |