2012-04-24 3 views
7

Ho un JCombobox nel mio codice. Ho aggiunto il FocusLost event. Ma non ha sparato comunque. Ho provato un sacco di tempo ma non ho trovato la soluzione.JComboBox focusLost non è sparare, perché è così?

jcbItemType.addFocusListener(new java.awt.event.FocusAdapter() { 
    public void focusLost(java.awt.event.FocusEvent evt) { 
     jcbItemTypeFocusLost(evt); 
    } 
}); 

private void jcbItemTypeFocusLost(java.awt.event.FocusEvent evt)          
    {           
     // TODO add your handling code here: 
     System.out.println("name=" + ((Component) evt.getSource()).getName()); 
     System.out.println("index=" + jcbItemType.getSelectedIndex()); 
    } 

Ma niente è stampato in console. Per favore suggeriscimi cosa sto facendo male.

risposta

6
  • FocusListener non è corretta Listener per JComboBox, tutto con un altro Listener(s) possono creare loop infinito (soprattutto modificabile JComboBox),

  • FocusListener è asincrona, a volte è troppo difficile da catturare eventi è gli ordini giusti soprattutto nei casi che JComponents ha aggiunto un altro esempio Listener(s) troppo

come l'ascolto per Focus dal derivato JTextField/JFormattedTextField

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

public class ComboBoxTwo extends JFrame implements ItemListener { 

    private static final long serialVersionUID = 1L; 
    private JComboBox mainComboBox; 
    private JComboBox subComboBox; 

    public ComboBoxTwo() { 
     String[] items = {"Select Item", "Color", "Shape", "Fruit"}; 
     String[] subItems1 = {"Select Color", "Red", "Blue", "Green"}; 
     mainComboBox = new JComboBox(items); 
     mainComboBox.addItemListener(this); 
     mainComboBox.addFocusListener(fcsListener); 
     add(mainComboBox, BorderLayout.WEST); 
     subComboBox = new JComboBox(subItems1); 
     subComboBox.setPrototypeDisplayValue("XXXXXXXXXXXXXXXXXXX"); 
     subComboBox.addItemListener(this); 
     add(subComboBox, BorderLayout.EAST); 
    } 

    @Override 
    public void itemStateChanged(ItemEvent e) { 
     if (e.getStateChange() == ItemEvent.SELECTED) { 
      if (e.getSource() == mainComboBox) { 
       System.out.println("Source : mainComboBox"); 
      } else if (e.getSource() == subComboBox) { 
       System.out.println("Source : subComboBox"); 
      } 
     } 
    } 

    public static void main(String[] args) { 
     SwingUtilities.invokeLater(new Runnable() { 

      @Override 
      public void run() { 
       JFrame frame = new ComboBoxTwo(); 
       frame.setDefaultCloseOperation(EXIT_ON_CLOSE); 
       frame.pack(); 
       frame.setLocationRelativeTo(null); 
       frame.setVisible(true); 
      } 
     }); 
    } 
// 
    private FocusListener fcsListener = new FocusListener() { 

     @Override 
     public void focusGained(FocusEvent e) { 
      dumpInfo(e); 
     } 

     @Override 
     public void focusLost(FocusEvent e) { 
      dumpInfo(e); 
     } 

     private void dumpInfo(FocusEvent e) { 
      System.out.println("Source : " + name(e.getComponent())); 
      System.out.println("Opposite : " + name(e.getOppositeComponent())); 
      System.out.println("Temporary: " + e.isTemporary()); 
      final Component c = e.getComponent();//works for editable JComboBox too 
      if (c instanceof JFormattedTextField) { 
       SwingUtilities.invokeLater(new Runnable() { 

        @Override 
        public void run() { 
         ((JFormattedTextField) c).selectAll(); 
        } 
       }); 
      } else if (c instanceof JTextField) { 
       SwingUtilities.invokeLater(new Runnable() { 

        @Override 
        public void run() { 
         ((JTextField) c).selectAll(); 
        } 
       }); 
      } 
     } 

     private String name(Component c) { 
      return (c == null) ? null : c.getName(); 
     } 
    }; 
} 
+0

ho usato in precedenza 'itemStateChanged' ma è problematico per il mio scopo e, quindi, voglio usare evento FocusLost. Il tuo esempio non ha funzionato per me anche se hai commenti come * // funziona anche per JComboBox modificabile *. Ma non sta funzionando per me. Si prega di avvisare. Lo sto cercando da molto tempo. – sarwar026

+0

@ sarwar026 in questa forma funziona come mi aspettavo, il riposo è notato nella mia risposta, utilizzare ItemListener per JComboBox, per esempio nella forma come ho postato qui, – mKorbel

+0

@ sarwar026 semplice non mi capito il motivo per cui per motivo dovete focusListener richiesta , per una migliore aiuto prima modificare la tua domanda con un [SSCCE] (http://sscce.org/) – mKorbel

5

ho trovato un modo molto semplice per risolvere questo problema.

L'editor di default di JComboBox ha una classe interna BasicComboBoxEditor $ BorderlessTextField che è il componente che ottiene e perde lo stato attivo.

Vi si può accedere semplicemente

Component component = comboBox.getEditor().getEditorComponent(); 
if (component instanceof JTextField) 
    JTextField borderlesstextfield = (JTextField) borderless; 

quindi aggiungere un ascoltatore attenzione come si farebbe per qualsiasi JTextField

borderlesstextfield.addFocusListener(new FocusListener() 
{ 
    public void focusGained(FocusEvent e) 
    { 
    } 
    public void focusLost(FocusEvent e) 
    { 
    } 
}}); 

Ora avete un focusListener che risponderà come previsto per guadagnare e la perdita di messa a fuoco per il controllo ComboBox

+0

Questo ha funzionato perfettamente e dovrebbe essere la risposta accettata dal momento che è molto meno complicata! – Xerus