控制台程序。
为了标识元素的类型,可以为菜单已提供的4中元素定义常量,用作ID。这有助于执行菜单项监听器的操作,还提供了一种标识颜色类型的方式。我们会累积许多应用程序范围的常量,所以把它们定义为可以静态导入的类中的静态域会比较方便。为了导入静态域,类必须在指定的包中,所以先建立包。
为了把类放在Constants包中,需要在硬盘的合适位置建立以Constants命名的目录,然后在编译Constants包中的类时,使用-classpath选项标识Constants目录的路径。
1 //Defines application wide constants
2 packageConstants;3 importjava.awt.Color;4
5 public classSketcherConstants {6 //Element type definitions
7 public final static int LINE = 101;8 public final static int RECTANGLE = 102;9 public final static int CIRCLE = 103;10 public final static int CURVE = 104;11
12 //Initial conditions
13 public final static int DEFAULT_ELEMENT_TYPE =LINE;14 public final static Color DEFAULT_ELEMENT_COLOR =Color.BLUE;15 }
将上述代码保存为Constants目录下的SketcherConstants.java。类中的每个元素类型ID都是整数常量,并且值都是唯一的。
1 //Main window for the Sketcher application
2 import javax.swing.*;3 import static java.awt.event.InputEvent.*; //For modifier constants
4 import java.awt.event.*;5 importjava.awt.Color;6 import static java.awt.Color.*;7 import static Constants.SketcherConstants.*;8
9 @SuppressWarnings("serial")10 public class SketcherFrame extendsJFrame {11 //Constructor
12 publicSketcherFrame(String title) {13 setTitle(title); //Set the window title
14 setJMenuBar(menuBar); //Add the menu bar to the window
15 setDefaultCloseOperation(EXIT_ON_CLOSE);16
17
18 JMenu fileMenu = new JMenu("File"); //Create File menu
19 JMenu elementMenu = new JMenu("Elements"); //Create Elements menu
20 fileMenu.setMnemonic('F'); //Create shortcut
21 elementMenu.setMnemonic('E'); //Create shortcut22
23 //Construct the file drop-down menu
24 newItem = fileMenu.add("New"); //Add New item
25 openItem = fileMenu.add("Open"); //Add Open item
26 closeItem = fileMenu.add("Close"); //Add Close item
27 fileMenu.addSeparator(); //Add separator
28 saveItem = fileMenu.add("Save"); //Add Save item
29 saveAsItem = fileMenu.add("Save As..."); //Add Save As item
30 fileMenu.addSeparator(); //Add separator
31 printItem = fileMenu.add("Print"); //Add Print item32
33 //Add File menu accelerators
34 newItem.setAccelerator(KeyStroke.getKeyStroke('N',CTRL_DOWN_MASK ));35 openItem.setAccelerator(KeyStroke.getKeyStroke('O', CTRL_DOWN_MASK));36 saveItem.setAccelerator(KeyStroke.getKeyStroke('S', CTRL_DOWN_MASK));37 printItem.setAccelerator(KeyStroke.getKeyStroke('P', CTRL_DOWN_MASK));38
39 //Construct the Elements drop-down menu
40 elementMenu.add(lineItem = new JRadioButtonMenuItem("Line", elementType==LINE));41 elementMenu.add(rectangleItem = new JRadioButtonMenuItem("Rectangle", elementType==RECTANGLE));42 elementMenu.add(circleItem = new JRadioButtonMenuItem("Circle", elementType==CIRCLE));43 elementMenu.add(curveItem = new JRadioButtonMenuItem("Curve", elementType==CURVE));44 ButtonGroup types = newButtonGroup();45 types.add(lineItem);46 types.add(rectangleItem);47 types.add(circleItem);48 types.add(curveItem);49
50 //Add element type accelerators
51 lineItem.setAccelerator(KeyStroke.getKeyStroke('L', CTRL_DOWN_MASK));52 rectangleItem.setAccelerator(KeyStroke.getKeyStroke('E', CTRL_DOWN_MASK));53 circleItem.setAccelerator(KeyStroke.getKeyStroke('I', CTRL_DOWN_MASK));54 curveItem.setAccelerator(KeyStroke.getKeyStroke('V', CTRL_DOWN_MASK));55
56 elementMenu.addSeparator();57 JMenu colorMenu = new JMenu("Color"); //Color submenu
58 elementMenu.add(colorMenu); //Add the submenu
59 colorMenu.add(redItem = new JCheckBoxMenuItem("Red", elementColor.equals(RED)));60 colorMenu.add(yellowItem = new JCheckBoxMenuItem("Yellow", elementColor.equals(YELLOW)));61 colorMenu.add(greenItem = new JCheckBoxMenuItem("Green", elementColor.equals(GREEN)));62 colorMenu.add(blueItem = new JCheckBoxMenuItem("Blue", elementColor.equals(BLUE)));63 ButtonGroup colors = new ButtonGroup(); //Color menu items button group
64 colors.add(redItem);65 colors.add(yellowItem);66 colors.add(greenItem);67 colors.add(blueItem);68
69 //Add element color accelerators
70 redItem.setAccelerator(KeyStroke.getKeyStroke('R', CTRL_DOWN_MASK));71 yellowItem.setAccelerator(KeyStroke.getKeyStroke('Y', CTRL_DOWN_MASK));72 greenItem.setAccelerator(KeyStroke.getKeyStroke('G', CTRL_DOWN_MASK));73 blueItem.setAccelerator(KeyStroke.getKeyStroke('B', CTRL_DOWN_MASK));74
75 //Add type menu item listeners
76 lineItem.addActionListener(newTypeListener(LINE));77 rectangleItem.addActionListener(newTypeListener(RECTANGLE));78 circleItem.addActionListener(newTypeListener(CIRCLE));79 curveItem.addActionListener(newTypeListener(CURVE));80
81 //Add color menu item listeners
82 redItem.addActionListener(newColorListener(RED));83 yellowItem.addActionListener(newColorListener(YELLOW));84 greenItem.addActionListener(newColorListener(GREEN));85 blueItem.addActionListener(newColorListener(BLUE));86
87 menuBar.add(fileMenu); //Add the file menu
88 menuBar.add(elementMenu); //Add the element menu
89 }90
91 //Handles element type menu items
92 class TypeListener implementsActionListener {93 //Constructor
94 TypeListener(inttype) {95 this.type =type;96 }97
98 //Sets the element type
99 public voidactionPerformed(ActionEvent e) {100 elementType =type;101 }102
103 private int type; //Store the type for the menu
104 }105
106 //Handles color menu items
107 class ColorListener implementsActionListener {108 publicColorListener(Color color) {109 this.color =color;110 }111
112 public voidactionPerformed(ActionEvent e) {113 elementColor =color;114 }115
116 privateColor color;117 }118
119 private JMenuBar menuBar = new JMenuBar(); //Window menu bar120
121 //File menu items
122 privateJMenuItem newItem, openItem, closeItem,123 saveItem, saveAsItem, printItem;124
125 //Element menu items
126 private JRadioButtonMenuItem lineItem, rectangleItem, circleItem, //Types
127 curveItem, textItem;128 private JCheckBoxMenuItem redItem, yellowItem, //Colors
129 greenItem, blueItem ;130 private Color elementColor = DEFAULT_ELEMENT_COLOR; //Current element color
131 private int elementType = DEFAULT_ELEMENT_TYPE; //Current element type
132 }
Sketcher类和以前一样:
1 //Sketching application
2 import javax.swing.*;3 import java.awt.*;4 import java.awt.event.*;5
6 public classSketcher {7 public static voidmain(String[] args) {8 theApp = new Sketcher(); //Create the application object
9 SwingUtilities.invokeLater(newRunnable() {10 public voidrun() {11 theApp.createGUI(); //Call GUI creator
12 }13 });14 }15
16 //Method to create the application GUI
17 private voidcreateGUI() {18 window = new SketcherFrame("Sketcher"); //Create the app window
19 Toolkit theKit = window.getToolkit(); //Get the window toolkit
20 Dimension wndSize = theKit.getScreenSize(); //Get screen size21
22 //Set the position to screen center & size to half screen size
23 window.setSize(wndSize.width/2, wndSize.height/2); //Set window size
24 window.setLocationRelativeTo(null); //Center window
25
26 window.addWindowListener(new WindowHandler()); //Add window listener
27 window.setVisible(true);28 }29
30 //Handler class for window events
31 class WindowHandler extendsWindowAdapter {32 //Handler for window closing event
33 @Override34 public voidwindowClosing(WindowEvent e) {35 window.dispose(); //Release the window resources
36 System.exit(0); //End the application
37 }38 }39
40 private SketcherFrame window; //The application window
41 private static Sketcher theApp; //The application object
42 }
构建元素对象时,使用elementType和elementColor成员来设置每个菜单项的状态。只选中了对应于elementType中设置的默认类型的元素类型菜单项,因为只有这个比较生成了true,作为JRadioButtonMenuItem构造函数的参数。
因为现在有自己的包来包含SketcherConstants类定义,所以必须使用-classpath选项,告诉编译器在哪里能找到这个类。假定Constants目录是C:/Packages目录的子目录,当前目录中包含Sketcher.java和SketcherFrame.java文件,可以使用下列命令编译Sketcher:
javac -classpath ".;c:/Packages" Sketcher.java
-classpath选项定义了两条路径:当前路径,由句点指定;C:/Packages,这是包含源文件Sketcher.java的Constants目录的路径。这个命令应编译所有的代码,包括自定义的包。