KeyEvent - Probleme

  • Themenstarter Themenstarter Gast
  • Beginndatum Beginndatum
Status
Nicht offen für weitere Antworten.
G

Gast

Gast
Hallo!

Ich schreibe gerade einen Login Dialog. Drückt man im Benutzername - Textfeld die Enter Taste, dann soll das Passwortfeld den Fokus erhalten und drückt man im Passwortfeld die Enter Taste, dann soll der Ok - Button den Fokus
erhalten. Sollte beim Login irgendetwas schief laufen, dann möchte ich, dass ein Dialog angezeigt wird, der den Benutzer vom Fehlschlagen des Logins informiert, beide Eingabefelder gelöscht werden und das Textfeld für die Eingabe des Benutzernamens den Fokus erhält.

Das Problem liegt nun darin, dass bei fehlgeschlagenem Login nicht das Benutzername - Textfeld den Fokus erhält, sondern das Passwortfeld. Offensichtlich wird das Drücken der Enter - Taste des Ok - Buttons bzw. des Buttons im Dialog nocheinmal verarbeitet, sobald das Benutzername - Textfeld den Fokus erhält.

Das Problem tritt nur dann auf, wenn man die Buttons mit der Enter - Taste betätigt anstatt die Maus zu verwenden.


Folgendes Demo -Programm zeigt das beschriebene Verhalten:

Code:
public class KeyEventDemo extends JDialog implements ActionListener
{
    private JTextField username;
    private JPasswordField password;
    private JButton okButton;

    public KeyEventDemo()
    {
        try
        {
            UIManager.setLookAndFeel("com.sun.java.swing.plaf.windows.WindowsLookAndFeel");
        } catch (Exception ex)
        {

        }

        KeyListener keyListener = new KeyListener();

        getContentPane().setLayout(new FlowLayout());
        username = new JTextField(10);
        username.addKeyListener(keyListener);
        getContentPane().add(username);

        password = new JPasswordField(10);
        password.addKeyListener(keyListener);
        getContentPane().add(password);

        okButton = new JButton("Ok");
        okButton.setActionCommand("BTN_OK");
        okButton.addActionListener(this);
        getContentPane().add(okButton);

        setSize(130, 120);
        setLocationRelativeTo(null);
        setVisible(true);
    }

    public void actionPerformed(ActionEvent e)
    {
        if (e.getActionCommand().equals("BTN_OK") )
        {
            JOptionPane.showMessageDialog(null, "Login fehlgeschlagen!");
            username.setText("");
            password.setText("");
            username.requestFocus();
        }
    }

    private class KeyListener extends KeyAdapter
    {
        public void keyReleased(KeyEvent e)
        {
            if (e.getKeyCode() == KeyEvent.VK_ENTER)
            {
                if ( e.getSource() instanceof JPasswordField)
                    okButton.requestFocus();
                else if (e.getSource() instanceof JTextField)
                    password.requestFocus();
            }
        }
    }

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


Vielen Dank für Eure Hilfe!
 
Das Problem liegt nun darin, dass bei fehlgeschlagenem Login nicht das Benutzername - Textfeld den Fokus erhält, sondern das Passwortfeld. Offensichtlich wird das Drücken der Enter - Taste des Ok - Buttons bzw. des Buttons im Dialog nocheinmal verarbeitet, sobald das Benutzername - Textfeld den Fokus erhält.

Ich habe deine Demo ausprobiert - und sie tut etwas anders: Wenn ich mich beim ersten mal einloggen möchte, läuft alles so wie es sollte. Versuche ich es jedoch noch einmal, dann wird beim Drücken der Enter-Taste nach der Eingabe des Namens nicht zum Pwd-Feld geschaltet, sondern direkt Ok gedrückt... très étrange...

[/quote]
 
Hmm. Ich habe keine Ahnung. Ich kann dir nur so weit helfen, dass nach dem ersten Durchlauf (also nach dem das erste mal Ok gedrückt wurde) beim Drücken der Enter-Taste die "keyReleased" und die "actionPerformed" Methode gleichzeitig ausgeführt werden....

Ich könnte dir jedoch einen Rat geben (ob es hilft, weiß ich nicht, da ich jetzt meine Zeit mit Deutschhaushaufgaben versch... ähhh verbringen muss :### und es somit nicht testen kann):
Mir erscheint die Verbindung von ActionListener und J-Dialog etws spanisch (ich erstelle grundsätzlich für meine Listener Inner-Classes), vieleicht liegt da das Problem... ???:L (kann ich jedoch nicht rational begründen)

mfg Merlin
 
Ein fieser Fehler...

Alle KeyEvents werden derjenigen Component zugeschoben, welche den Fokus hat.
Wird nun im Message-Dialog Enter gedrückt, geschieht folgendes:

- ein "keyPressed"-Event wird verschickt. Der Button empfängt dieses Event
- Der Button verschickt ein ActionEvent. Damit schliesst der Dialog.
- Dadurch kann deine Implementation von "actionPerformed" weitermachen
- "username" erhält den Fokus
- ein "keyReleased"-Event wird verschickt, Deine Implementation empfängt es...

P.S. den Ablauf kannst du ganz schön sehen, wenn du die Enter-Taste ein paar Sekunden gedrückt hältst.


Man kann das verhindern, wenn man den Code ein bisschen abändert:
Code:
    private class KeyListener extends KeyAdapter{
      private KeyEvent pressed;
      
      public void keyPressed( KeyEvent e ){
        pressed = e;
      }
      
        public void keyReleased (KeyEvent e){
          if( pressed != null && pressed.getSource() == e.getSource() ){
            if (e.getKeyCode() == KeyEvent.VK_ENTER) {
              if (e.getSource() == password)
                okButton.requestFocus();
              else if (e.getSource() == username)
                password.requestFocus();
            }
          }
        }
    }

Wow, das ist mal ein Fehler!

mfg Beni
 
Hallo!

Vielen Dank für die Zeit, die Ihr in mein kleines aber lästiges Problem investiert habt - im Besonderen natürlich für die Lösung samt ausführlicher Erklärung.

Wow, das ist mal ein Fehler!

Freut mich, dass ich Euch auch mal ein wenig fordern konnte! :wink:

Grüsse,
--Alex
 
Du könntest aber auch aus dem "public void keyReleased..." ein "public void keyPressed..." machen, und alles andere so lassen wie es ist. Dann würde lediglich beoi gehaltener Return-Taste der Dialog mehrmals durchlaufen...
 
P.S.
@Gast
Nur so zum sagen...

... der Thrad ist 7 Monate alt, und wird wohl nicht mehr gelesen :wink:
 
Status
Nicht offen für weitere Antworten.

Neue Themen


Zurück
Oben