JButtons和JMenuItems在ActionListener中没有合作

时间:2013-10-04 05:44:03

标签: java swing actionlistener menuitem

大家好,这是我的第一篇文章!

我正在使用这个计算器项目作为教我自我java的工具。

我一般都试图重现Microsoft Windows 7 Calculator程序。

到目前为止一切顺利,除了更复杂的按钮之外,所有按钮都按照预期的方式工作 Microsoft计算器中的按钮功能几乎完全相同。

这是我的问题, 在使用以下代码

为JMenuBar实现actionlistener / event时
String menuText = ((JMenuItem) evt.getSource()).getText();

    if(menuText.equals("info")){
        System.out.println("it works");
        JOptionPane.showMessageDialog(null, "aha it works");

一切都在我周围坍塌!

这是完整的代码

public class Calculator extends JFrame implements ActionListener {

JButton backSpace, clear, one, two, three, four, five, six, seven, eight,
        nine, zero, period, devision, modulas, subtraction, addition,
        negative, equals;

Font myFont = new Font("ARIAL", Font.BOLD, 40);

JTextArea answerBox = new JTextArea("");

static double numberOne = 0;
static double numberTwo = 0;
static double result;
static String operator = null;

public Calculator() {
    super("Calculator");
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    setVisible(true);

    // set up components
    addition = new JButton("+");
    backSpace = new JButton("BACKSPACE");
    clear = new JButton("CLEAR");
    one = new JButton("1");
    two = new JButton("2");
    three = new JButton("3");
    four = new JButton("4");
    five = new JButton("5");
    six = new JButton("6");
    seven = new JButton("7");
    eight = new JButton("8");
    nine = new JButton("9");
    zero = new JButton("0");
    period = new JButton(".");
    devision = new JButton("/");
    modulas = new JButton("*");
    subtraction = new JButton("-");
    negative = new JButton("-N");
    equals = new JButton("=");

    // set up answerbox
    answerBox.setComponentOrientation(ComponentOrientation.RIGHT_TO_LEFT);
    answerBox.setFont(myFont);
    answerBox.setEditable(false);

    // set up actionListener
    backSpace.addActionListener(this);
    clear.addActionListener(this);
    one.addActionListener(this);
    two.addActionListener(this);
    three.addActionListener(this);
    four.addActionListener(this);
    five.addActionListener(this);
    six.addActionListener(this);
    seven.addActionListener(this);
    eight.addActionListener(this);
    nine.addActionListener(this);
    zero.addActionListener(this);
    period.addActionListener(this);
    devision.addActionListener(this);
    addition.addActionListener(this);
    modulas.addActionListener(this);
    subtraction.addActionListener(this);
    negative.addActionListener(this);
    equals.addActionListener(this);

    // menu
    JMenuBar menuBar = new JMenuBar();
    JMenu menu = new JMenu("About");
    JMenuItem info = new JMenuItem("Info");

    info.addActionListener(this);
    menu.add(info);
    menuBar.add(menu);
    setJMenuBar(menuBar);

    // set up layout
    GridBagLayout gridBag = new GridBagLayout();
    GridBagConstraints constraints = new GridBagConstraints();
    JPanel pane = new JPanel();
    pane.setLayout(gridBag);

    // default
    constraints.fill = GridBagConstraints.BOTH;
    constraints.anchor = GridBagConstraints.WEST;
    constraints.gridy = 0;
    constraints.gridx = 0;
    constraints.gridwidth = 1;
    constraints.gridheight = 1;
    constraints.weightx = 10;
    constraints.weighty = 10;
    constraints.insets = new Insets(2, 2, 2, 2);

    // answer box
    constraints.gridx = 0;
    constraints.gridy = 0;
    constraints.gridwidth = 6;
    answerBox.append("0");

    gridBag.setConstraints(answerBox, constraints);
    pane.add(answerBox);

    // backSPace
    constraints.gridx = 0;
    constraints.gridy = 1;
    constraints.gridwidth = 3;

    gridBag.setConstraints(backSpace, constraints);
    pane.add(backSpace);

    // clear

    constraints.anchor = GridBagConstraints.EAST;
    constraints.gridx = 3;
    constraints.gridy = 1;
    constraints.weightx = 10;
    gridBag.setConstraints(clear, constraints);
    pane.add(clear);

    // nine
    constraints.gridwidth = 1;
    constraints.weightx = 1;
    constraints.gridx = 0;
    constraints.gridy = 3;
    gridBag.setConstraints(nine, constraints);
    pane.add(nine);

    // eight
    constraints.gridx = 1;
    constraints.gridy = 3;
    gridBag.setConstraints(eight, constraints);
    pane.add(eight);

    // seven
    constraints.gridx = 2;
    constraints.gridy = 3;
    gridBag.setConstraints(seven, constraints);
    pane.add(seven);

    // devision
    constraints.gridwidth = 1;
    constraints.weightx = 1;
    constraints.gridx = 3;
    constraints.gridy = 3;
    constraints.anchor = GridBagConstraints.SOUTH;
    gridBag.setConstraints(devision, constraints);
    pane.add(devision);

    // EQUALS
    constraints.gridx = 4;
    constraints.gridy = 3;
    constraints.gridwidth = 2;
    constraints.gridheight = 4;
    constraints.weighty = 30;
    constraints.anchor = GridBagConstraints.SOUTH;
    gridBag.setConstraints(equals, constraints);
    pane.add(equals);

    // six
    constraints.weighty = 10;
    constraints.gridwidth = 1;
    constraints.gridheight = 1;
    constraints.gridx = 0;
    constraints.gridy = 4;
    gridBag.setConstraints(six, constraints);
    pane.add(six);

    // five
    constraints.gridx = 1;
    constraints.gridy = 4;
    gridBag.setConstraints(five, constraints);
    pane.add(five);

    // four
    constraints.gridwidth = 1;

    constraints.gridx = 2;
    constraints.gridy = 4;
    gridBag.setConstraints(four, constraints);
    pane.add(four);

    // Addition
    constraints.gridwidth = 1;
    constraints.weightx = 1;
    constraints.gridx = 3;
    constraints.gridy = 4;
    gridBag.setConstraints(addition, constraints);
    pane.add(addition);

    // three
    constraints.gridx = 0;
    constraints.gridy = 5;
    gridBag.setConstraints(three, constraints);
    pane.add(three);

    // two
    constraints.gridx = 1;
    constraints.gridy = 5;
    gridBag.setConstraints(two, constraints);
    pane.add(two);

    // one
    constraints.gridx = 2;
    constraints.gridy = 5;
    gridBag.setConstraints(one, constraints);
    pane.add(one);

    // subtraction
    constraints.gridx = 3;
    constraints.gridy = 5;
    gridBag.setConstraints(subtraction, constraints);
    pane.add(subtraction);

    // zero
    constraints.gridx = 0;
    constraints.gridy = 6;
    constraints.gridwidth = 2;
    gridBag.setConstraints(zero, constraints);
    pane.add(zero);

    // period
    constraints.gridx = 2;
    constraints.gridy = 6;
    constraints.gridwidth = 1;
    gridBag.setConstraints(period, constraints);
    pane.add(period);

    // multiplication
    constraints.gridx = 3;
    constraints.gridy = 6;
    constraints.gridwidth = 1;
    gridBag.setConstraints(modulas, constraints);
    pane.add(modulas);

    pack();
    add(pane);

}

public static void main(String[] args) {
    Calculator frame = new Calculator();
    frame.setSize(300, 350);
}

public void actionPerformed(ActionEvent evt){       
    Object source = evt.getSource();
    String menuText = ((JMenuItem) evt.getSource()).getText();

    if(menuText.equals("info")){
        System.out.println("it works");
        JOptionPane.showMessageDialog(null, "aha it works");
    }

    else if(source == one){
        answerBox.append("1");


    }else if (source == two){
        answerBox.append("2");
    }

    else if (source == three){
        answerBox.append("3");
    }

    else if (source == four){
        answerBox.append("4");
    }

    else if (source == five){
        answerBox.append("5");
    }

    else if (source == six){
        answerBox.append("6");
    }

    else if (source == seven){
        answerBox.append("7");
    }

    else if (source == eight){
        answerBox.append("8");
    }

    else if (source == nine){
        answerBox.append("9");
    }

    else if (source == zero){
        answerBox.append("0");
    }

    else if (source == addition){
        numberOne=Double.parseDouble(answerBox.getText());
        operator="+";
        answerBox.setText("");
    }   

    else if (source == subtraction){
        numberOne=Double.parseDouble(answerBox.getText());
        operator="-";
        answerBox.setText("");
        }

    else if (source == modulas){
        numberOne=Double.parseDouble(answerBox.getText());
        operator="*";
        answerBox.setText("");

    }
    else if (source == devision){
        numberOne=Double.parseDouble(answerBox.getText());
        operator="/";
        answerBox.setText("");

    }
    else if (source == period){
        answerBox.append(".");
    }

    else if(source == equals){

           numberTwo=Double.parseDouble(answerBox.getText());
           if(operator.equals("+"))
               result=numberOne+numberTwo;
           else if(operator.equals("-"))
               result=numberOne-numberTwo;
           else if(operator.equals("*"))
               result=numberOne-numberTwo;
           else if(operator.equals("/"))
               result=numberOne/numberTwo;

           answerBox.setText(" "+result);
           operator="=";

    }

    else if(source == clear){       
        numberOne=0;
        numberTwo=0;
        answerBox.setText("");
    }


}


}

3 个答案:

答案 0 :(得分:3)

String menuText = ((JMenuItem) evt.getSource()).getText();

我猜你在上面的语句中得到了ClassCastException。

该代码假定事件由JMenuItem生成。问题是您为JButtons和JMenuItem使用相同的ActionListener,因此您不能假设源对象是JMenuItem。

在单个ActionListener中实现所有代码并不是一个好主意。您可以为类似的函数共享ActionListener。例如,在以下代码中,按下数字按钮始终相同,因此您可以使用相同的侦听器:

import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.border.*;

public class ButtonCalculator extends JPanel
{
    private JButton[] buttons;
    private JTextField display;

    public ButtonCalculator()
    {
        Action numberAction = new AbstractAction()
        {
            @Override
            public void actionPerformed(ActionEvent e)
            {
                display.replaceSelection(e.getActionCommand());
            }
        };

        display = new JTextField();
        display.setEditable( false );
        display.setHorizontalAlignment(JTextField.RIGHT);

        JPanel buttonPanel = new JPanel();
        buttonPanel.setLayout( new GridLayout(0, 5) );
        buttons = new JButton[10];

        for (int i = 0; i < buttons.length; i++)
        {
            String text = String.valueOf(i);
            JButton button = new JButton( text );
            button.addActionListener( numberAction );
            buttons[i] = button;
            buttonPanel.add( button );

            //  Support Key Bindings

            KeyStroke pressed = KeyStroke.getKeyStroke(text);
            InputMap inputMap = button.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
            inputMap.put(pressed, text);
            button.getActionMap().put(text, numberAction);
        }

        setLayout( new BorderLayout() );
        add(display, BorderLayout.NORTH);
        add(buttonPanel, BorderLayout.SOUTH);
    }

    private static void createAndShowUI()
    {
        UIManager.put("Button.margin", new Insets(5, 10, 5, 10) );
        JFrame frame = new JFrame("Button Calculator");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add( new ButtonCalculator() );
        frame.setResizable( false );
        frame.pack();
        frame.setLocationByPlatform( true );
        frame.setVisible( true );
    }

    public static void main(String[] args)
    {
        EventQueue.invokeLater(new Runnable()
        {
            public void run()
            {
                createAndShowUI();
            }
        });
    }
}

对于您的其他动作(“+”,“ - ”......),您应该创建单独的侦听器。

答案 1 :(得分:1)

在将evt.getSource转换为JMenuItem之前,您必须检查源是否为JMenuItem。 改变你的方法actionPerformed一开始就像我的例子那样有效(你必须要求'Info'而不是'info')。 为camickr +1 - 不同的actionListener是提高代码质量的方法。

@Override
public void actionPerformed(ActionEvent evt) {
    Object source = evt.getSource();

    if (source.getClass() == JMenuItem.class) {
        String menuText = ((JMenuItem) evt.getSource()).getText();

        if (menuText.equals("info")) {
            System.out.println("it works");
            JOptionPane.showMessageDialog(null, "aha it works");
        }
    }
    else if (source == one) {
        answerBox.append("1");
    }

答案 2 :(得分:1)

有几件事情在我身上跳了出来......

您不能依赖源类型作为类的给定实例...

Object source = evt.getSource();
String menuText = ((JMenuItem) evt.getSource()).getText();

这可能会导致您ClassCastException

此外,Info!= info

您将菜单项定义为....

JMenuItem info = new JMenuItem("Info");

但你用它来测试它的文字内容......

if(menuText.equals("info")){
Java中的

String比较区分大小写(除非您使用equalsIgnoresCase

您应该提供并使用actionCommand属性。

例如......

JMenuItem info = new JMenuItem("Info");
info.setActionComand("infoMenu");

然后在你actionPeformed方法中,你可以做类似的事情......

if("infoMenu".equals(evt.getActionCommand())){...}

我还建议你看看How to use Actions,这些是非常强大的,孤立的动作,可以应用于应用程序的多个不同部分,包括菜单,按钮和键绑定API