/* * 1.1 version. */ import java.awt.*; import java.awt.event.*; import java.util.*; import java.applet.Applet; public class Converter extends Applet { ConversionPanel metricPanel, usaPanel; Unit[] metricDistances = new Unit[3]; Unit[] usaDistances = new Unit[4]; /** * Create the ConversionPanels (one for metric, another for U.S.). * I used "U.S." because although Imperial and U.S. distance * measurements are the same, this program could be extended to * include volume measurements, which aren't the same. */ public void init() { //Use a GridLayout with 2 rows, as many columns as necessary, //and 5 pixels of padding around all edges of each cell. setLayout(new GridLayout(2,0,5,5)); //Create Unit objects for metric distances, and then //instantiate a ConversionPanel with these Units. metricDistances[0] = new Unit("Centimeters", 0.01); metricDistances[1] = new Unit("Meters", 1.0); metricDistances[2] = new Unit("Kilometers", 1000.0); metricPanel = new ConversionPanel(this, "Metric System", metricDistances); //Create Unit objects for U.S. distances, and then //instantiate a ConversionPanel with these Units. usaDistances[0] = new Unit("Inches", 0.0254); usaDistances[1] = new Unit("Feet", 0.305); usaDistances[2] = new Unit("Yards", 0.914); usaDistances[3] = new Unit("Miles", 1613.0); usaPanel = new ConversionPanel(this, "U.S. System", usaDistances); //Add both ConversionPanels to the Converter. add(metricPanel); add(usaPanel); } /** * Does the conversion from metric to U.S., or vice versa, and * updates the appropriate ConversionPanel. */ void convert(ConversionPanel from) { ConversionPanel to; if (from == metricPanel) to = usaPanel; else to = metricPanel; double multiplier = from.getMultiplier() / to.getMultiplier(); to.setValue(multiplier * from.getValue()); } /** Draws a box around this panel. */ public void paint(Graphics g) { Dimension d = getSize(); g.drawRect(0,0, d.width - 1, d.height - 1); } /** * Puts a little breathing space between * the panel and its contents, which lets us draw a box * in the paint() method. */ public Insets getInsets() { return new Insets(5,5,5,5); } /** Executed only when this program runs as an application. */ public static void main(String[] args) { //Create a new window. Frame f = new Frame("Converter Applet/Application"); f.addWindowListener(new WindowAdapter() { public void windowClosing(WindowEvent e) { System.exit(0); } }); //Create a Converter instance. Converter converter = new Converter(); //Initialize the Converter instance. converter.init(); //Add the Converter to the window and display the window. f.add("Center", converter); f.pack(); //Resizes the window to its natural size. f.setVisible(true); } } class ConversionPanel extends Panel implements ActionListener, AdjustmentListener, ItemListener { TextField textField; Choice unitChooser; Scrollbar slider; int max = 10000; int block = 100; Converter controller; Unit[] units; ConversionPanel(Converter myController, String myTitle, Unit[] myUnits) { //Initialize this ConversionPanel to use a GridBagLayout. GridBagConstraints c = new GridBagConstraints(); GridBagLayout gridbag = new GridBagLayout(); setLayout(gridbag); //Save arguments in instance variables. controller = myController; units = myUnits; //Set up default layout constraints. c.fill = GridBagConstraints.HORIZONTAL; //Add the label. It displays this panel's title, centered. Label label = new Label(myTitle, Label.CENTER); c.gridwidth = GridBagConstraints.REMAINDER; //It ends a row. gridbag.setConstraints(label, c); add(label); //Add the text field. It initially displays "0" and needs //to be at least 10 columns wide. textField = new TextField("0", 10); c.weightx = 1.0; //Use maximum horizontal space... c.gridwidth = 1; //The default value. gridbag.setConstraints(textField, c); add(textField); textField.addActionListener(this); //Add the pop-up list (Choice). unitChooser = new Choice(); for (int i = 0; i < units.length; i++) { //Populate it. unitChooser.add(units[i].description); } c.weightx = 0.0; //The default value. c.gridwidth = GridBagConstraints.REMAINDER; //End a row. gridbag.setConstraints(unitChooser, c); add(unitChooser); unitChooser.addItemListener(this); //Add the slider. It's horizontal, and it has the maximum //value specified by the instance variable max. Its initial //and minimum values are the default (0). A click increments //the value by block units. slider = new Scrollbar(Scrollbar.HORIZONTAL); slider.setMaximum(max + 10); slider.setBlockIncrement(block); c.gridwidth = 1; //The default value. gridbag.setConstraints(slider, c); add(slider); slider.addAdjustmentListener(this); } /** * Returns the multiplier (units/meter) for the currently * selected unit of measurement. */ double getMultiplier() { int i = unitChooser.getSelectedIndex(); return units[i].multiplier; } /** Draws a box around this panel. */ public void paint(Graphics g) { Dimension d = getSize(); g.drawRect(0,0, d.width - 1, d.height - 1); } /** * Puts a little breathing space between * the panel and its contents, which lets us draw a box * in the paint() method. * We add more pixels to the right, to work around a * Choice bug. */ public Insets getInsets() { return new Insets(5,5,5,8); } /** * Gets the current value in the text field. * It's guaranteed to be the same as the value * in the scroller (subject to rounding, of course). */ double getValue() { double f; try { f = (double)Double.valueOf(textField.getText()).doubleValue(); } catch (java.lang.NumberFormatException e) { f = 0.0; } return f; } public void actionPerformed(ActionEvent e) { setSliderValue(getValue()); controller.convert(this); } public void itemStateChanged(ItemEvent e) { controller.convert(this); } /** Respond to the slider. */ public void adjustmentValueChanged(AdjustmentEvent e) { textField.setText(String.valueOf(e.getValue())); controller.convert(this); } /** Set the values in the slider and text field. */ void setValue(double f) { setSliderValue(f); textField.setText(String.valueOf((float)f)); } /** Set the slider value. */ void setSliderValue(double f) { int sliderValue = (int)f; if (sliderValue > max) sliderValue = max; if (sliderValue < 0) sliderValue = 0; slider.setValue(sliderValue); } } class Unit { String description; double multiplier; Unit(String description, double multiplier) { super(); this.description = description; this.multiplier = multiplier; } public String toString() { String s = "Meters/" + description + " = " + multiplier; return s; } }