2012-01-04 5 views
4

私は以下のコードに示すJComboBoxを持っています。プログラムが起動すると、actionPerformedイベントがただちに起動し、いくつかのヌルポインタ例外が発生します。そのため、選択した要素のどれもから開始しません。しかし、何らかの理由でそれがうまくいかない(私が何をしても "USD/TRY"を表示することから始まる)。誰もが考えている?頑固なJComboBox

JComboBox comboBox = new JComboBox(new String[]{"USD/TRY", "EUR/TRY", "GBP/TRY"}); 

comboBox.setSelectedIndex(-1); // doesnt change anything 
comboBox.setSelectedIndex(2); // doesnt change anything  
comboBox.setSelectedItem(null); // doesnt change anything 

UPDATE:

public class MainFrame { 

    private final JTextArea textArea = new JTextArea(); 
    private IExchangeSource s; 

    public MainFrame(final IExchangeSource s) { 
     //build gui 
     final JComboBox comboBox = new JComboBox(); 

     comboBox.addItem("USD/TRY"); 
     comboBox.addItem("EUR/TRY"); 
     comboBox.addItem("GBP/TRY"); 

     comboBox.setSelectedIndex(-1); // doesnt change anything 
     //comboBox.setSelectedIndex(2); // doesnt change anything 


     JFrame f = new JFrame("Currency Converter"); 
     JPanel p = new JPanel(new BorderLayout()); 
     textArea.setName("textarea"); 
     textArea.setWrapStyleWord(true); 
     textArea.setLineWrap(true); 
     this.s = s; 

     comboBox.addActionListener(new ActionListener() { 

      public void actionPerformed(ActionEvent e) { 
       String exchange = (String) comboBox.getSelectedItem(); 

       s.getData(exchange); 
      } 
     }); 

     p.add(comboBox, BorderLayout.NORTH); 
     p.add(textArea, BorderLayout.CENTER); 
     f.setPreferredSize(new Dimension(300, 300)); 
     f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
     f.pack(); 
     f.add(p); 
     comboBox.setSelectedIndex(0); 
     f.setVisible(true); 
    } 
} 
+0

JComboBoxの作成後にString []をロードしてみてください。 –

+0

試してみましたが、どちらも問題ありません。/それに応じて質問を更新しました。ありがとう – Cemre

+3

例外のスタックトレースを持つことが役に立ちます。どのようにしてまだ作成されていないコンボボックスにActionListenerを追加できますか? –

答えて

7

あなたの(不完全)の例では、右の任意の以前の設定を解除する、可視になる前

comboBox.setSelectedIndex(0); 

を呼び出します。希望の初期インデックスを、リスナーを追加する前にの前に設定し、EDTで開始することを無視しないでください(sscce)。

import java.awt.BorderLayout; 
import java.awt.Dimension; 
import java.awt.EventQueue; 
import java.awt.event.ActionEvent; 
import java.awt.event.ActionListener; 
import javax.swing.JComboBox; 
import javax.swing.JFrame; 
import javax.swing.JPanel; 
import javax.swing.JTextArea; 

public class MainFrame { 

    private final JTextArea textArea = new JTextArea(); 


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

      @Override 
      public void run() { 
       new MainFrame(); 
      } 
     }); 
    } 
    public MainFrame() { 
     //build gui 
     final JComboBox comboBox = new JComboBox(); 

     comboBox.addItem("USD/TRY"); 
     comboBox.addItem("EUR/TRY"); 
     comboBox.addItem("GBP/TRY"); 

     JFrame f = new JFrame("Currency Converter"); 
     JPanel p = new JPanel(new BorderLayout()); 
     textArea.setName("textarea"); 
     textArea.setWrapStyleWord(true); 
     textArea.setLineWrap(true); 

     comboBox.setSelectedIndex(-1); 
     comboBox.addActionListener(new ActionListener() { 

      @Override 
      public void actionPerformed(ActionEvent e) { 
       System.out.println(comboBox.getSelectedItem() + ": " + e); 
      } 
     }); 

     p.add(comboBox, BorderLayout.NORTH); 
     p.add(textArea, BorderLayout.CENTER); 
     f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
     f.pack(); 
     f.setSize(new Dimension(300, 300)); 
     f.add(p); 
     f.setVisible(true); 
    } 
} 
+1

ありがとうございます。他の答えはある程度問題を解決しましたが、まだ解決できた問題はいくつか残っていました。私はフレームを構築するためのinvokeLater関数の欠如(すなわち、EDTで始まる)が主な問題であったと思う。 – Cemre

+0

フォローアップしていただきありがとうございます。私はいつもEDT問題を明らかにする新しい方法に興味を持っています。 – trashgod

+0

@Cemre、あなたはこれまでにAPIとチュートリアルを読んだことがありますか?このチュートリアルの例では、EDTを正しく使用しているので、チュートリアルの時間を先に指摘しています。 – camickr

2

1)ItemListener代わりのActionListenerが、常にこのItemListenerを追加します。のような下のコンボボックスを構築すると、ここでどちらか

JComboBox comboBox = new JComboBox(); 

comboBox.addItem("USD/TRY"); 
comboBox.addItem("EUR/TRY"); 
comboBox.addItem("GBP/TRY"); 

何も変更doesntのSSCCEがあります2回のイベントを発生させたSELECTEDDESELECTED

myComboBox.addItemListener(new ItemListener() { 

     @Override 
     public void itemStateChanged(ItemEvent e) { 
      if (e.getStateChange() == ItemEvent.SELECTED) { 
       //some stuff 
      } 
     } 
    }); 

2)あなたのGUIが多分あるかEventDispashThread上で作成されていないが、この場合には重要ではありません、あなたは)invokeLater(にwrapingすることによって、この方法を遅らせる必要があり、例えば

public class MainFrame { 
    . 
    . 
    . 

    f.setPreferredSize(new Dimension(300, 300)); 
    f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
    f.pack(); 
    f.add(p); 
    comboBox.setSelectedIndex(0); 
    f.setVisible(true); 
    selectDesiredItem(); 
} 

private void selectDesiredItem() { 
    EventQueue.invokeLater(new Runnable() { 

     @Override 
     public void run() { 
      comboBox.setSelectedIndex(-1); 
     } 
    }); 
} 
より良い

3)CcyPairsがデフォルトで四辺を持っているかもしれない重要な

4)が、通貨ペアのための実装AutoCompete JComboBox/JTextFieldだろう

  • Buy BaseCcy

  • Sell BaseCcy

  • Buy VariableCcy

  • Sell VariableCcy

+0

詳細な回答をいただきありがとうございます。ほんとうにありがとう。あなたが2番目の提案は、コンボボックスのエラーを解決したが、私はまだnullポインタの例外を取得していた。 – Cemre

+0

+1の主題専門知識! – trashgod

+0

-1あまりにも多くのランダムな箇条書きのために - 幸せな新年:-) – kleopatra

0

の提案はこれまでのところ良いです。物事は本当にコンポーネントを構築しますどのように回旋されている場合しかし、時には、より直接的な修正が必要とされている:

  1. サブクラス(Swingクラスがイベントを発火されているものや、JListの、など...)JComboBoxの
  2. フィールドを追加、private boolean fireEvents = false;それをvolatileにすることを検討してください。
  3. 「主要なオーバーホールが」後で新しい、こうした新しいファイルをロードするのと、呼び出された場合fireEvents
  4. の状態を確認するために、関連するfireXXX()方法が唯一のすべての建設と初期化後fireEvents = trueを設定し、オーバーライドは
  5. 完了すべての再構築中にfireEventsをfalseに戻すことができます。
+0

ありがとう、あなたの答えをありがとう。 – Cemre

+0

-1 _事が複雑になると、アプリケーションコードが何か間違っているからです。そのため、ランダムな暗黙のサブクラス化、ぎこちなしのフラグや曖昧なオーバーライドの代わりに、具体的なコンテキストで正確に何が間違っているのかを把握して理解しておくことが最善の方法です_that_ – kleopatra

関連する問題