代码之家  ›  专栏  ›  技术社区  ›  Oussama Mahjour

Java Swing:ATM初始化身份验证类后未检测到接口密钥事件

  •  0
  • Oussama Mahjour  · 技术社区  · 1 年前

    我正在构建一个ATM模拟器,我希望在按下ENTER键时验证PIN码。但是,我遇到了一个问题,在初始化Authentication类之后,在ATM_Interface类中没有检测到关键事件。以下是我的代码的相关部分:

    public class Main{
      public static void main(String[] args){
           JFrame frame = new JFrame();
           ATM_Interface atm=new ATM_Interface();
           frame.setVisible(true);
           frame.setDefaultCloseOperation(3);
           frame.setLayout(null);
           frame.add(atm);
           frame.pack();
    }
    }
    
    public class ATM_Interface extends JPanel {
      static String Status="";
      
       public ATM_Interface(){
    
      
        this.setPreferredSize(new Dimension(200,200));
        this.setBackground(Color.blue);
        this.setBounds(115,67,340,340);
        this.addKeyListener(new keyAdapter());
        this.setFocusable(true);
        Authentication auth = new Authentication();  
        this.requestFocusInWindow();
                  
       }
    
    
      
       class keyAdapter extends KeyAdapter{
             @Override
            public void     keyPressed(KeyEvent e){
               switch(Status){
                case "authentication":
                break;
                default:
                add(auth);
                Status="authentication";
                
              }
             System.out.println("test");
             }
    
           
                   
    
             
       }
      
     } 
    
    public class Authentication extends  JPanel {        
        JTextField input = new  JTextField();
       public Authentication(){
            input.setPreferredSize(new Dimension(100,50));
            this.add(input);
    
       }
       public boolean getAcces(){
         if(input.getText().equals("0234")){
              return true;
         }
         else return false;
       }
       
    }
    
    

    在这段代码中,ATM_Interface JPanel应该使用KeyAdapter捕获关键事件。但是,在初始化Authentification类并将其作为子组件添加到ATM_Interface之后,在ATM_Interface JPanel中没有检测到关键事件。

    我已经尝试过使用requestFocusInWindow()和setFocusable()将焦点设置为ATM_Interface面板,但似乎无法解决问题。 如何确保在ATM_Interface JPanel中检测到关键事件?任何帮助都将不胜感激!

    1 回复  |  直到 1 年前
        1
  •  2
  •   MadProgrammer    1 年前

    我希望在按下ENTER键时验证PIN码

    简单的答案是使用 ActionListener 当用户“操作”文本字段(即,在大多数情况下,按下 进来 字段聚焦时的键)

    一个最小的、可复制的例子。。。

    import java.awt.EventQueue;
    import java.awt.GridBagLayout;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import javax.swing.JFrame;
    import javax.swing.JOptionPane;
    import javax.swing.JPanel;
    import javax.swing.JTextField;
    import javax.swing.border.EmptyBorder;
    
    public class Main {
        public static void main(String[] args) {
            new Main();
        }
    
        public Main() {
            EventQueue.invokeLater(new Runnable() {
                @Override
                public void run() {
                    JFrame frame = new JFrame("Test");
                    frame.add(new TestPane());
                    frame.pack();
                    frame.setLocationRelativeTo(null);
                    frame.setVisible(true);
                }
            });
        }
    
        protected class TestPane extends JPanel {
    
            private JTextField pinField;
    
            public TestPane() {
                setBorder(new EmptyBorder(32, 32, 32, 32));
                setLayout(new GridBagLayout());
    
                pinField = new JTextField(4);
                add(pinField);
    
                pinField.addActionListener(new ActionListener() {
                    @Override
                    public void actionPerformed(ActionEvent e) {
                        String pinText = pinField.getText();
                        try {
                            int pinValue = Integer.parseInt(pinText);
                            if (pinValue != 1234) {
                                JOptionPane.showMessageDialog(TestPane.this, "Invalid PIN", "Error", JOptionPane.ERROR_MESSAGE);
                            } else {
                                // Now I'd use an observer here to notify interested
                                // parties that the pin was validated
                            }
                        } catch (NumberFormatException exp) {
                            JOptionPane.showMessageDialog(TestPane.this, "Invalid PIN", "Error", JOptionPane.ERROR_MESSAGE);
                        }
                    }
                });
            }
    
        }
    }
    

    看见

    了解更多详细信息。

    我还建议看一下 Implementing a Document Filter 如果您有兴趣限制用户可以在文本字段中输入的内容(即实时验证)。这也允许您在PIN达到所需位数后“自动”验证PIN。

    您还应该花时间学习和使用可用的 layout managers ,这只会为你节省很多时间和头痛。

        2
  •  1
  •   g00se    1 年前

    下面这样的东西应该为你做。请参阅Javadoc DocumentListener

    import javax.swing.JPanel;
    import javax.swing.JTextField;
    import java.awt.Dimension;
    import javax.swing.event.DocumentListener;
    import javax.swing.event.DocumentEvent;
    
    public class Authentication extends JPanel implements DocumentListener {
        JTextField input = new JTextField();
    
        public Authentication() {
            input.setPreferredSize(new Dimension(100, 30));
            input.getDocument().addDocumentListener(this);
            this.add(input);
        }
    
        @Override
        public void changedUpdate(DocumentEvent e) {
            if (getAccess()) {
                doOnAccess();
            }
        }
    
        @Override
        public void insertUpdate(DocumentEvent e) {
            if (getAccess()) {
                doOnAccess();
            }
        }
    
        @Override
        public void removeUpdate(DocumentEvent e) {
            if (getAccess()) {
                doOnAccess();
            }
        }
    
        private void doOnAccess() {
            System.out.println("Yes, we're in!");
        }
    
        public boolean getAccess() {
            return (input.getText().equals("0234"));
        }
    
    }