home *** CD-ROM | disk | FTP | other *** search
Java Source | 1996-08-14 | 8.7 KB | 308 lines |
- /*
- * Copyright (c) 1996 by Jan Andersson, Torpa Konsult AB.
- *
- * Permission to use, copy, and distribute this software for
- * NON-COMMERCIAL purposes and without fee is hereby granted
- * provided that this copyright notice appears in all copies.
- *
- */
-
- import java.awt.Color;
- import java.awt.image.ImageConsumer;
- import java.awt.image.ImageProducer;
- import java.awt.image.ColorModel;
- import java.awt.image.IndexColorModel;
- import java.util.Hashtable;
- import java.io.InputStream;
- import java.io.StringBufferInputStream;
-
- /**
- * This class is an implementation of the ImageProducer interface that
- * uses a X11 bitmap (xbm) array, X11 pixmap (xpm) array or an input
- * stream to a xbm/xpm file to produce pixel values for an Image.
- *
- * Here is a few examples: which creates an image from a xbm-file: "foo.xbm".
- * The forground is set to blue and the Component background is used.
- * <pre>
- * // create image from inline xbm data using transparent color.
- * // I.e no background specied.
- * static private int[] arrow = {
- * 0x3f, 0x0f, 0x0f, 0x1f, 0x39, 0x71, 0xe0, 0xc0
- * };
- * Image image = createImage(
- * new XImageSource(8, 8, arrow, Color.black, nil, true));
- *
- * // create image from xpm-file "foo.xpm"
- * FileInputStream is = new FileInputStream("foo.xpm");
- * Image image = createImage(new XImageSource(is));
- *
- * </pre>
- *
- * @see ImageProducer
- *
- * @version 1.1 96/02/20
- * @author Jan Andersson, Torpa Konsult AB. (janne@torpa.se)
- */
- public class XImageSource implements ImageProducer {
- int width;
- int height;
- byte pixels[];
-
- ColorModel colorModel;
- private boolean error = false;
- private ImageConsumer theConsumer;
-
- /**
- * Constructs an ImageProducer object from an X11 style bitmap (xbm)
- * to produce data for an Image object.
- * @param w width
- * @param h height
- * @param bits bitmap in xbm format
- * @param fg foreground color
- * @param bg background color (if trans is false)
- * @param trans transparent if true
- */
- public XImageSource(int w, int h, int[] bits,
- Color fg, Color bg, boolean trans) {
- xbmInitialize(w, h, bits, fg, bg, trans);
- }
-
- /**
- * Constructs an ImageProducer object from an X11 style bitmap (xbm)
- * input stream to produce data for an Image object.
- * @param is input stream to xbm data
- * @param fg foreground color
- * @param bg background color (if trans is false)
- * @param trans transparent if true
- */
- public XImageSource(InputStream is,
- Color fg, Color bg, boolean trans) {
- // Use XbmParser to parse input stream
- XbmParser parser = new XbmParser(is);
- if (parser.parse())
- xbmInitialize(parser.getWidth(), parser.getHeight(),
- parser.getBitmap(), fg, bg, trans);
- else
- error = true;
- }
-
- /**
- * Constructs an ImageProducer object from an X11 style pixmap (xpm)
- * consisting of an array of strings.
- * @param data string array in xpm format.
- */
- public XImageSource(String[] data) {
-
- // create string buffer from data array
- StringBuffer strBuf = new StringBuffer(1024);
- for (int i=0; i<data.length; i++)
- strBuf.append("\"" + data[i] + "\"\n");
-
- // create an input stream from the string buffer
- StringBufferInputStream is =
- new StringBufferInputStream(strBuf.toString());
-
- // Use XpmParser to parse input stream
- XpmParser parser = new XpmParser(is);
- if (parser.parse())
- xpmInitialize(parser.getWidth(), parser.getHeight(),
- parser.getPixmap(), parser.getColorTable());
- else
- error = true;
- }
- /**
- * Constructs an ImageProducer object from an X11 style pixmap (xpm)
- * input stream to produce data for an Image object.
- * @param is input stream to xpm data
- */
- public XImageSource(InputStream is) {
- // Use XpmParser to parse input stream
- XpmParser parser = new XpmParser(is);
- if (parser.parse())
- xpmInitialize(parser.getWidth(), parser.getHeight(),
- parser.getPixmap(), parser.getColorTable());
- else
- error = true;
- }
-
- /**
- * Initialize pixels from the xbm bitmap, using the provided colors
- * as foreground/background
- */
- private void xbmInitialize(int w, int h, int[] bits,
- Color fg, Color bg,
- boolean trans) {
- width = w;
- height = h;
-
- // create color map
- byte colormap[] = new byte[6];
- int transIndex = -1;
- // color component 0 is for background
- if (trans) {
- // color component 0: transparent
- transIndex = 0;
- colormap[0] = 0;
- colormap[1] = 0;
- colormap[2] = 0;
- }
- else {
- // color component 0: background
- colormap[0] = (byte) bg.getRed();
- colormap[1] = (byte) bg.getGreen();
- colormap[2] = (byte) bg.getBlue();
- }
- // color component 1: foreground
- colormap[3] = (byte) fg.getRed();
- colormap[4] = (byte) fg.getGreen();
- colormap[5] = (byte) fg.getBlue();
-
- // create color model
- colorModel = new IndexColorModel(8, 2, colormap, 0, false, transIndex);
-
- // allocate pixels
- pixels = new byte[width*height];
-
- // loop for xbm bitmap and create pixels
- int index = 0;
- int byteIndex = 0;
- int jMax = width/8;
- try {
- for (int i=0; i<height; i++) {
- for (int j=0; j<jMax; j++) {
- byte bitByte = (byte) bits[byteIndex];
- for (int k=0; k<8; k++) {
- int pixel = bitByte & (1 << k);
- pixels[index] = (pixel != 0) ? (byte) 1 : (byte) 0;
- index++;
- }
- byteIndex++;
- }
- }
- }
- catch (Exception e) {
- error = true; // error
- }
- }
-
- /**
- * Initialize pixels from the xpm pixmap.
- */
- private void xpmInitialize(int w, int h, byte[] pixels,
- Color[] colorTable) {
- width = w;
- height = h;
- this.pixels = pixels;
-
- // create color map
- int nColors = colorTable.length;
- int cmSize = 3 * nColors;
- byte colormap[] = new byte[cmSize];
-
- // init color map
- int transIndex = -1;
- for (int i=0; i<nColors; i++) {
- if (colorTable[i] == null) {
- // transparent color
- transIndex = i;
- }
- else {
- colormap[3*i] = (byte) colorTable[i].getRed();
- colormap[3*i+1] = (byte) colorTable[i].getGreen();
- colormap[3*i+2] = (byte) colorTable[i].getBlue();
- }
- }
-
- // create color model
- colorModel = new IndexColorModel(8, nColors, colormap,
- 0, false, transIndex);
- }
-
- /**
- * Adds an ImageConsumer to the list of consumers interested in
- * data for this image.
- * @see ImageConsumer
- */
- public synchronized void addConsumer(ImageConsumer ic) {
- theConsumer = ic;
- produce();
- theConsumer = null;
- }
-
- /**
- * Determine if an ImageConsumer is on the list of consumers currently
- * interested in data for this image.
- * @return true if the ImageConsumer is on the list; false otherwise
- * @see ImageConsumer
- */
- public synchronized boolean isConsumer(ImageConsumer ic) {
- return (ic == theConsumer);
- }
-
- /**
- * Remove an ImageConsumer from the list of consumers interested in
- * data for this image.
- * @see ImageConsumer
- */
- public synchronized void removeConsumer(ImageConsumer ic) {
- if (theConsumer == ic) {
- theConsumer = null;
- }
- }
-
- /**
- * Adds an ImageConsumer to the list of consumers interested in
- * data for this image, and immediately start delivery of the
- * image data through the ImageConsumer interface.
- * @see ImageConsumer
- */
- public void startProduction(ImageConsumer ic) {
- addConsumer(ic);
- }
-
- /**
- * Requests that a given ImageConsumer have the image data delivered
- * one more time in top-down, left-right order.
- * @see ImageConsumer
- */
- public void requestTopDownLeftRightResend(ImageConsumer ic) {
- // Not needed. The data is always in TDLR format.
- }
-
- /*
- * Produce Image data.
- * I.e set the data for the Image, using the ImageConsumer interface.
- */
- private void produce() {
- if (theConsumer != null) {
- theConsumer.setDimensions(width, height);
- }
- if (theConsumer != null) {
- theConsumer.setProperties(new Hashtable());
- }
- if (theConsumer != null) {
- theConsumer.setColorModel(colorModel);
- }
- if (theConsumer != null) {
- theConsumer.setHints(ImageConsumer.TOPDOWNLEFTRIGHT |
- ImageConsumer.COMPLETESCANLINES |
- ImageConsumer.SINGLEPASS |
- ImageConsumer.SINGLEFRAME);
- }
- if (theConsumer != null) {
- theConsumer.setPixels(0, 0, width, height,
- colorModel,
- pixels, 0, width);
- }
- if (theConsumer != null) {
- if (!error) {
- theConsumer.imageComplete(ImageConsumer.STATICIMAGEDONE);
- }
- else {
- theConsumer.imageComplete(ImageConsumer.IMAGEERROR);
- }
- }
- }
- }
-
-