EventHandler表现奇怪而怪异的色块

时间:2017-05-05 19:52:26

标签: java swing

我有一个功课,我应该创建一个应用程序,将卡塔里里亚尔的钱转换为3种选择中的一种(美元,欧元或英镑)。

我想成为一个很酷的男孩,给我的应用程序一个背景标题和图标。但它还不够,我还决定没有提交按钮来开始计算。我在输入字段中添加了一个键侦听器,因此它将在运行时计算。正如您将在下面的代码中看到的,我添加了一个catch,以防输入是一个数字以外的东西,但无论我输入什么,我得到错误消息,并提到奇怪的补丁。

我想知道如何摆脱那些烦人的色块,为什么不管输入中有什么错误出现?请记住,这是不完整的我知道,我只是想知道如何解决我的问题,然后继续前进。

截图 https://gyazo.com/f4fbde1274311498f7381a43192bc85d https://gyazo.com/ba90c38dbc4d12f029a1bfe6cadf955a

代码:

package convertor;

import java.awt.Color;
import java.awt.Font;
import java.awt.Toolkit;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;

import javax.swing.ButtonGroup;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JRadioButton;
import javax.swing.JTextField;

public class MoneyConvertorTemp {

    public static void main(String[] args) {
        new MoneyConvertorTemp();   
    }

    private MoneyConvertorTemp() {

        JFrame frame = new JFrame();
        frame.setTitle("Q2W Convertor");
        frame.setIconImage(Toolkit.getDefaultToolkit().getImage(MoneyConvertorTemp.class.getResource("/convertor/logo.png")));
        frame.setBounds(100, 100, 470, 250);
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.getContentPane().setLayout(null);
        frame.setResizable(false);

        JPanel mainPanel = new JPanel();
        mainPanel.setBounds(0, 0, 464, 221);
        frame.getContentPane().add(mainPanel);
        mainPanel.setLayout(null);
        mainPanel.setBackground(new Color(0, 0, 0, 100));

        JLabel background = new JLabel("");
        background.setIcon(new ImageIcon(MoneyConvertorTemp.class.getResource("/convertor/image.jpg")));
        background.setBounds(0, 0, 464, 221);
        frame.getContentPane().add(background);     

        JLabel headerLbl = new JLabel("Qatri to Western Money Convertor");
        headerLbl.setFont(new Font("Traditional Arabic", Font.BOLD | Font.ITALIC, 28));
        headerLbl.setForeground(new Color(0,100,0));
        headerLbl.setBounds(10, 11, 451, 32);
        mainPanel.add(headerLbl);       

        ButtonGroup currencyChoicesBtnGroup = new ButtonGroup();
        JRadioButton usdRadBtn = new JRadioButton("QR to USD");
        usdRadBtn.setBackground(new Color(50, 42, 42));
        usdRadBtn.setForeground(Color.WHITE);
        usdRadBtn.setFont(new Font("Tahoma", Font.BOLD, 14));
        currencyChoicesBtnGroup.add(usdRadBtn);
        usdRadBtn.setSelected(true);
        usdRadBtn.setBounds(308, 68, 131, 23);
        mainPanel.add(usdRadBtn);

        JRadioButton euroRadBtn = new JRadioButton("QR to Euros");
        euroRadBtn.setBackground(new Color(50, 42, 42));
        euroRadBtn.setForeground(Color.WHITE);
        euroRadBtn.setFont(new Font("Tahoma", Font.BOLD, 14));
        currencyChoicesBtnGroup.add(euroRadBtn);
        euroRadBtn.setBounds(308, 94, 131, 23);
        mainPanel.add(euroRadBtn);

        JRadioButton poundsRadBtn = new JRadioButton("QR to pounds");
        poundsRadBtn.setBackground(new Color(50, 42, 42));
        poundsRadBtn.setForeground(Color.WHITE);
        poundsRadBtn.setFont(new Font("Tahoma", Font.BOLD, 14));
        currencyChoicesBtnGroup.add(poundsRadBtn);
        poundsRadBtn.setBounds(308, 120, 131, 23);
        mainPanel.add(poundsRadBtn);

        JLabel qrLbl = new JLabel("Qatri Riyal");
        qrLbl.setForeground(Color.black);
        qrLbl.setFont(new Font("Tahoma", Font.BOLD, 18));
        qrLbl.setBounds(27, 74, 104, 32);
        mainPanel.add(qrLbl);

        JLabel resultsLbl = new JLabel("");
        resultsLbl.setForeground(Color.BLACK);
        resultsLbl.setFont(new Font("Tahoma", Font.BOLD, 18));
        resultsLbl.setBounds(27, 126, 242, 32);
        mainPanel.add(resultsLbl);

        JTextField inputFld = new JTextField();
        inputFld.setBounds(141, 71, 149, 46);
        mainPanel.add(inputFld);
        inputFld.setColumns(10);

        JLabel errorLbl = new JLabel("");
        errorLbl.setFont(new Font("Tahoma", Font.BOLD, 12));
        errorLbl.setForeground(Color.RED);
        errorLbl.setBounds(37, 154, 253, 23);
        errorLbl.setVisible(false);
        mainPanel.add(errorLbl);

        frame.setVisible(true);

        inputFld.addKeyListener(new KeyAdapter() {
            @Override
            public void keyPressed(KeyEvent a) {

                double input;
                errorLbl.setVisible(false);
                errorLbl.setText("");

                try {
                    input = Double.parseDouble(inputFld.getText());
                } catch (NumberFormatException e) {
                    errorLbl.setText("Input has to be a number");
                    errorLbl.setVisible(true);
                    return;
                }       
            }
        }); 

    }

}

2 个答案:

答案 0 :(得分:2)

  

奇怪的色块

mainPanel.setBackground(new Color(0, 0, 0, 100));

Swing无法正确绘制透明色。

使用透明颜色打破了Swing绘画的规则,该规则要求组件不透明或不透明。

因此,您需要进行自定义绘画,以确保首先绘制背景。类似的东西:

JPanel panel = new JPanel()
{
    protected void paintComponent(Graphics g)
    {
        g.setColor( getBackground() );
        g.fillRect(0, 0, getWidth(), getHeight());
        super.paintComponent(g);
    }
};
panel.setOpaque(false); // background of parent will be painted first
panel.setBackground( new Color(255, 0, 0, 20) );
frame.add(panel);

查看Backgrounds With Transparency以获取更多信息,并查看可重复使用的课程,为您执行此绘画。

编辑:

  

我在输入字段中添加了一个键侦听器,因此它会在运行时计算。

不要使用KeyListener。这是一个古老的AWT解决方案。 Swing拥有更新更好的API。

相反,您可以使用DocumentListener。这将在添加或删除文本时生成事件。阅读How to Write a DocumentListener上Swing教程中的部分,了解更多信息和工作示例,以便开始使用。

答案 1 :(得分:0)

要回答有关错误出现原因的问题(@camick已回答了背景/颜色问题),我相信您需要在keyReleased中实施KeyListener方法,而不是{ {1}}方法。

在更新组件文本之前会触发

keyPressed,因此keyPressed将返回组件的旧文本。

我不是100%确定是这种情况,但值得测试。使用getText也可以使用,并且可以避免在按下keyTyped等键时触发错误。或者,您可以查询事件以查看按下了哪个键并将其添加到shift返回的值,但由于您在此处使用低级键处理,因此您需要担心退格键和删除键等问题。 / p>