home *** CD-ROM | disk | FTP | other *** search
Java Source | 1996-08-14 | 7.4 KB | 349 lines |
-
- /*
- * ImageButton.java
- *
- * Copyright (C) 1996 Shaun Terry. All Rights Reserved.
- */
-
- package spt.gui;
-
- import java.awt.Panel;
- import java.awt.Graphics;
- import java.awt.Font;
- import java.awt.Event;
- import java.awt.Color;
- import java.awt.Image;
- import java.awt.FontMetrics;
- import java.awt.Toolkit;
- import java.applet.AudioClip;
-
- import spt.gui.Rectangle3D;
- import spt.gui.ImagePanel;
-
-
- /**
- * A push button with an image on it. A text label
- * may also be displayed.
- *
- * @author Shaun Terry
- */
-
- public class ImageButton extends Panel {
-
- private boolean isDown = false;
- private int borderW = Rectangle3D.borderWidthOfMode(Rectangle3D.IN);
-
- /** Left of the image */
- public static final int LEFT = 0;
-
- /** Top of the image */
- public static final int TOP = 1;
-
- /** Right of the image */
- public static final int RIGHT = 2;
-
- /** Bottom of the image */
- public static final int BOTTOM = 3;
-
-
- private String label;
- private Image img;
- private Image inactive_img;
- private Image shadowed_img;
- private float imageScale = 1;
- private AudioClip audio;
-
- private boolean fShowBorder = true;
- private boolean fDrawPushedIn = true;
-
- private int pos = RIGHT;
- private int padding = 2;
- private int gap = 0;
-
- private int ix=0, iy=0, iw=0, ih=0; // Internal image info
-
- public ImageButton(Image image) {
- this(image, null);
- }
-
- /** A null image or label is ok; a null image <em>and</em> label
- * is pretty darn useless.
- */
- public ImageButton(Image image, String label) {
- this.label = label;
- setLayout(null);
- img = image;
- resize();
- }
-
- public synchronized void addNotify() {
- resize();
- super.addNotify();
- }
-
- public void setFont(Font f) {
- super.setFont(f);
- resize();
- }
-
- /** Show the border of the button? Useful when you just want
- * the image without the 3D button look around it.
- */
- public void setShowBorder(boolean b) {
- fShowBorder = b;
- if (b) borderW = Rectangle3D.borderWidthOfMode(Rectangle3D.IN);
- else borderW = 0;
- resize();
- }
-
- /** Make the button "depress" when clicked? If false the button
- * will behave normally, except when pushed it will give no
- * visual feedback.
- */
- public void setDrawPushedIn(boolean b) {
- fDrawPushedIn = b;
- }
-
- public int getLabelPosition() { return pos; }
-
- /** Set the position of the label in relation to the image:
- * TOP, LEFT, RIGHT or BOTTOM.
- */
- public void setLabelPosition(int a) {
- if (a != LEFT && a != TOP && a != RIGHT && a != BOTTOM)
- throw new IllegalArgumentException();
- pos = a;
- resize();
- }
-
- public String getLabel() { return label; }
-
- public void setLabel(String l) {
- label = l;
- resize();
- repaint();
- }
-
- /** Set the audio clip to play when the button is pushed.
- */
- public void setAudioClip(AudioClip a) {
- audio = a;
- }
-
- /** Set the padding, in pixels, between the button border and
- * its image.
- */
- public void setPadding(int p) {
- padding = p;
- resize();
- repaint();
- }
-
- public int getPadding() { return padding; }
-
- /** Set the gap, in pixels, between the label, if any, and image.
- */
- public void setImageLabelGap(int g) {
- gap = g;
- resize();
- repaint();
- }
-
- public int getImageLabelGap() { return gap; }
-
- /** The image to be shown.
- */
- public void setImage(Image i) {
- if (i == null || img == null) { img = i; resize(); }
- else if (i.getWidth(this) != img.getWidth(this) ||
- i.getHeight(this) != img.getHeight(this)) {
- img = i;
- // If new image has a different size, then resize
- resize();
- }
- else img = i;
-
- repaintImage();
- }
-
- /** Scale the image to the given value (1.0 = 100%).
- */
- public void setImageScale(double f) { setImageScale((float) f); }
-
- /** Scale the image to the given value (1.0 = 100%).
- */
- public void setImageScale(float pct) {
- if (pct <= 0) pct = 1;
- imageScale = pct;
- resize();
- }
-
- /** Enables the button.
- */
- public void enable() {
- if (!isEnabled()) {
- isDown = false;
- super.enable();
- repaint();
- }
- }
-
- /** Disables the button. A grayed-out version of the image is
- * shown.
- */
- public void disable() {
- if (isEnabled()) {
- isDown = false;
- super.disable();
- repaint();
- }
- }
-
- /** Resize the button the the size of its image plus padding
- * and border.
- */
- public void resize() {
- Font f = getFont();
- FontMetrics fm = null;
- if (f != null && label != null)
- fm = getToolkit().getFontMetrics(f);
-
- int iw=0, ih=0, _gap=0;
-
- if (img != null) {
- iw = (int) (img.getWidth(this) * imageScale);
- ih = (int) (img.getHeight(this) * imageScale);
- _gap = gap;
- }
-
- int w, h;
- w = iw + (2*(padding+borderW));
- h = ih + (2*(padding+borderW));
-
- if (fm != null) {
- if (pos == LEFT || pos == RIGHT) {
- w += _gap + fm.stringWidth(label);
-
- // Cuz the text could be taller than the image
- h = Math.max(h, fm.getAscent() + (2*(padding+borderW)));
- }
- else {
- h += _gap + fm.getAscent();
-
- // Cause the text could be wider than the image
- w = Math.max(w, fm.stringWidth(label) + (2*(padding+borderW)));
- }
- }
-
- resize(w, h);
- }
-
- protected void repaintImage() {
- if (img != null) {
- Graphics g = getGraphics();
- if (g == null) return;
- g.clearRect(ix, iy, iw, ih);
- if (imageScale == 1)
- g.drawImage(isEnabled() ? img : inactive_img, ix, iy, this);
- else g.drawImage(isEnabled() ? img : inactive_img, ix, iy, iw, ih, this);
- }
- }
-
- public synchronized void paint(Graphics g) {
- if (!isEnabled() && inactive_img == null) {
- inactive_img = ImagePanel.createDisabledImage(img, this);
- }
-
- int w = size().width;
- int h = size().height;
-
- if (fShowBorder) {
- Rectangle3D r = new Rectangle3D(this, 0, 0, w, h);
-
- if (isDown && fDrawPushedIn) r.setDrawingMode(Rectangle3D.IN);
- else r.setDrawingMode(Rectangle3D.OUT);
-
- r.paint(g);
- }
-
- int o = padding + borderW + ((isDown && fDrawPushedIn) ? 1 : 0);
-
- iw=0; ih=0;
- int _gap=0;
-
- if (img != null) {
- iw = (int) (img.getWidth(this) * imageScale);
- ih = (int) (img.getHeight(this) * imageScale);
- _gap = gap;
- }
-
- FontMetrics fm=null;
-
- if (label != null) {
- fm = getFontMetrics(getFont());
-
- if (pos == RIGHT) ix = o;
- else if (pos == LEFT) ix = o + _gap + fm.stringWidth(label);
- else ix = (int) ((w-iw)/2) + ((isDown && fDrawPushedIn) ? 1 : 0);
-
- if (pos == TOP) iy = o + _gap + fm.getAscent();
- else if (pos == BOTTOM) iy = o;
- else iy = (int) ((h-ih)/2) + ((isDown && fDrawPushedIn) ? 1 : 0);
- }
- else { ix = iy = o; }
-
- repaintImage();
-
- int x, y;
- if (label != null) {
-
- if (pos == LEFT) x = o;
- else if (pos == RIGHT) x = o + _gap + iw;
- else x = (int) ((w-fm.stringWidth(label))/2)
- + ((isDown && fDrawPushedIn) ? 1 : 0);
-
- if (pos == TOP) y = o + fm.getAscent();
- else if (pos == BOTTOM) y = o + _gap + fm.getAscent() + ih;
- else y = h - (int) ((h-fm.getAscent())/2)
- + ((isDown && fDrawPushedIn) ? 1 : 0) - 1;
-
- g.setColor(getForeground());
-
- if (!isEnabled()) {
- g.setColor(Color.white);
- g.drawString(label, x+1, y+1);
- g.setColor(getBackground().darker());
- }
-
- g.drawString(label, x, y);
- }
- }
-
- public boolean mouseDown(Event e, int x, int y) {
- if (isEnabled()) {
- isDown = true;
- repaint();
- if (audio != null) audio.play();
- }
- return true;
- }
-
- public boolean mouseUp(Event e, int x, int y) {
- if (isEnabled() && isDown) {
- isDown = false;
- repaint();
- e.id = Event.ACTION_EVENT;
- postEvent(e);
- }
- return true;
- }
-
- public boolean mouseExit(Event e, int x, int y) {
- if (isEnabled() && isDown) {
- isDown = false;
- repaint();
- }
- return true;
- }
- }
-