3

休憩に費やした時間を尋ねる GUI ウィンドウがあります。私が取得したい結果は、たとえば、1:15 - int 時間 = 1 および int 分 = 15 - [続行] ボタンをクリックした後です。JComboBox と JButton を一緒に動作させることができないため、得られる結果は数時間または数分です (私はそう思います)。また、ユーザーが数字を入力したのか無効な入力をしたのかを確認する方法がよくわかりません。コードは次のとおりです。

@SuppressWarnings("serial")
public class FormattedTextFields extends JPanel implements ActionListener {

    private int hours;
    private JLabel hoursLabel;
    private JLabel minsLabel;
    private static String hoursString = " hours: ";
    private static String minsString = " minutes: ";
    private JFormattedTextField hoursField;
    private NumberFormat hoursFormat;

    public FormattedTextFields() {

        super(new BorderLayout());
        hoursLabel = new JLabel(hoursString);
        minsLabel = new JLabel(minsString);
        hoursField = new JFormattedTextField(hoursFormat);
        hoursField.setValue(new Integer(hours));
        hoursField.setColumns(10);
        hoursLabel.setLabelFor(hoursField);
        minsLabel.setLabelFor(minsLabel);

        JPanel fieldPane = new JPanel(new GridLayout(0, 2));

        JButton cntButton = new JButton("Continue");
        cntButton.setActionCommand("cnt");
        cntButton.addActionListener(this);
        JButton prevButton = new JButton("Back");

        String[] quarters = { "15", "30", "45" };

        JComboBox timeList = new JComboBox(quarters);
        timeList.setSelectedIndex(2);
        timeList.addActionListener(this);

        fieldPane.add(hoursField);
        fieldPane.add(hoursLabel);
        fieldPane.add(timeList);
        fieldPane.add(minsLabel);
        fieldPane.add(prevButton);
        fieldPane.add(cntButton);

        setBorder(BorderFactory.createEmptyBorder(20, 20, 20, 20));
        add(fieldPane, BorderLayout.CENTER);
    }

    private static void createAndShowGUI() {    
        JFrame frame = new JFrame("FormattedTextFieldDemo");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add(new FormattedTextFields());
        frame.pack();
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                UIManager.put("swing.boldMetal", Boolean.FALSE);
                createAndShowGUI();
            }
        });
    }

    @Override
    public void actionPerformed(ActionEvent e) {    
        if (e.getActionCommand().equalsIgnoreCase("cnt")) {

        hours = ((Number) hoursField.getValue()).intValue();
        minutes = Integer.parseInt(timeList.getSelectedItem().toString());

        // \d mean every digit charater
        Pattern p = Pattern.compile("\\d");
        Matcher m = p.matcher(hoursField.getValue().toString());
        if (m.matches()) {
            System.out.println("Hours: " + hours);
            System.out.println("Minutes: " + minutes);
        } else {
            hoursField.setValue(0);
            JOptionPane.showMessageDialog(null, "Numbers only please.");
        }
        }
    }

} // end class

--EDIT--
更新された ActionPerformed メソッド

4

3 に答える 3

7

ActionListener がメソッドを呼び出して保持している値を抽出できるようにするには、アクション リスナーに表示されるコンボ ボックスへの有効な参照が必要です。現在、JComboBox はクラスのコンストラクターで宣言されているため、コンストラクターでのみ表示され、他の場所では表示されません。これを解決するには、コンボ ボックスをクラス フィールドにする必要があります。つまり、メソッドやコンストラクターではなく、クラス自体で宣言する必要があります。

例えば:

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

public class Foo002 extends JPanel implements ActionListener {

   JComboBox combo1 = new JComboBox(new String[]{"Fe", "Fi", "Fo", "Fum"});
   public Foo002() {

      JComboBox combo2 = new JComboBox(new String[]{"One", "Two", "Three", "Four"});
      JButton helloBtn = new JButton("Hello");

      helloBtn.addActionListener(this); // I really hate doing this!

      add(combo1);
      add(combo2);
      add(helloBtn);
   }

   private static void createAndShowGUI() {
      JFrame frame = new JFrame("FormattedTextFieldDemo");
      frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
      frame.add(new Foo002());
      frame.pack();
      frame.setVisible(true);
   }

   public static void main(String[] args) {
      SwingUtilities.invokeLater(new Runnable() {
         public void run() {
            UIManager.put("swing.boldMetal", Boolean.FALSE);
            createAndShowGUI();
         }
      });
   }

   @Override
   public void actionPerformed(ActionEvent e) {
      // this works because combo1 is visible in this method 
      System.out.println(combo1.getSelectedItem().toString());

      // this doesn't work because combo2's scope is limited to 
      // the constructor and it isn't visible in this method.
      System.out.println(combo2.getSelectedItem().toString());
   }

}
于 2012-02-26T00:43:23.663 に答える
3

解析数テストの場合、次の 2 つのソリューションがあります。

最初:

try{
    Integer.parseInt(myString);
catch(Exception e){
    System.out.print("not a number");
}

2番目:そして、よりクリーンな方法は正規表現を使用することだと思います:

// \d mean every digit charater you can find a full description [here][1] 
Pattern p = Pattern.compile("\\d");
Matcher m = p.matcher( myString );
if( m.matches() ){
    //it's a number
}else{
    //it's not a number
}

より強力な正規表現を行いたい場合は、このJava regex testerをご覧ください。

おやすみ&おやすみなさい

PS: グラフィック要素間の相互作用に問題はありません。グラフィック オブジェクトの参照を保持する必要があるだけです。

于 2012-02-26T00:54:39.317 に答える
2

このスニペットを確認し、NumberFormat に関する情報を提供するためにいくつかのコメントを追加し、[続行] ボタンをクリックして時間を表示します。あなたが適用したいチェックのタイプなので、単純な JTextField でそれを行いました。このために JFormattedTextField は必要ありません。

import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.event.*;
import javax.swing.text.*;
public class FormattedTextFields extends JPanel implements ActionListener 
{

    private int hours;
    private JLabel hoursLabel;
    private JLabel minsLabel;
    private static String hoursString = " hours: ";
    private static String minsString = " minutes: ";
    private JComboBox timeList;
    private JTextField hoursField;

    public FormattedTextFields() 
    {
        super(new BorderLayout());

        hoursLabel = new JLabel(hoursString);
        minsLabel = new JLabel(minsString);
        hoursField = new JTextField();
        //hoursField.setValue(new Integer(hours));
        hoursField.setColumns(10);
        hoursLabel.setLabelFor(hoursField);
        minsLabel.setLabelFor(minsLabel);
        Document doc = hoursField.getDocument();
        if (doc instanceof AbstractDocument)
        {
            AbstractDocument abDoc  = (AbstractDocument) doc;
            abDoc.setDocumentFilter(new DocumentInputFilter());
        }

        JPanel fieldPane = new JPanel(new GridLayout(0, 2));

        JButton cntButton = new JButton("Continue");
        cntButton.setActionCommand("cnt");
        cntButton.addActionListener(this);
        JButton prevButton = new JButton("Back");

        String[] quarters = { "15", "30", "45" };

        /*
         * Declared timeList as an Instance Variable, so that 
         * it can be accessed inside the actionPerformed(...)
         * method.
         */
        timeList = new JComboBox(quarters);
        timeList.setSelectedIndex(2);
        timeList.addActionListener(this);

        fieldPane.add(hoursField);
        fieldPane.add(hoursLabel);
        fieldPane.add(timeList);
        fieldPane.add(minsLabel);
        fieldPane.add(prevButton);
        fieldPane.add(cntButton);

        setBorder(BorderFactory.createEmptyBorder(20, 20, 20, 20));
        add(fieldPane, BorderLayout.CENTER);
    }

    private static void createAndShowGUI() 
    {    
        JFrame frame = new JFrame("FormattedTextFieldDemo");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add(new FormattedTextFields());
        frame.pack();
        frame.setVisible(true);
    }

    public static void main(String[] args) 
    {
        SwingUtilities.invokeLater(new Runnable() 
        {
            public void run() 
            {
                UIManager.put("swing.boldMetal", Boolean.FALSE);
                createAndShowGUI();
            }
        });
    }

    @Override
    public void actionPerformed(ActionEvent e) 
    {

        String time = "";
        if (e.getActionCommand().equalsIgnoreCase("cnt")) 
        {
            hours = Integer.parseInt(hoursField.getText());
            time = hours + " : " + ( (String) timeList.getSelectedItem());
            System.out.println(time);
        }
    }

    /*
     * This class will check for any invalid input and present 
     * a Dialog Message to user, for entering appropriate input.
     * you can let it make sound when user tries to enter the
     * invalid input. Do see the beep() part for that inside 
     * the class's body.
     */
    class DocumentInputFilter extends DocumentFilter
    {
        public void insertString(FilterBypass fb
                    , int offset, String text, AttributeSet as) throws BadLocationException
        {
            int len = text.length();
            if (len > 0)
            {
                /* Here you can place your other checks
                 * that you need to perform and do add
                 * the same checks for replace method
                 * as well.
                 */
                if (Character.isDigit(text.charAt(len - 1)))
                    super.insertString(fb, offset, text, as);
                else 
                {
                    JOptionPane.showMessageDialog(null, "Please Enter a valid Integer Value."
                                                            , "Invalid Input : ", JOptionPane.ERROR_MESSAGE);
                    Toolkit.getDefaultToolkit().beep();
                }   
            }                                               
        }

        public void replace(FilterBypass fb, int offset
                            , int length, String text, AttributeSet as) throws BadLocationException
        {
            int len = text.length();
            if (len > 0)
            {
                if (Character.isDigit(text.charAt(len - 1)))
                    super.replace(fb, offset, length, text, as);
                else 
                {
                    JOptionPane.showMessageDialog(null, "Please Enter a valid Integer Value."
                                                            , "Invalid Input : ", JOptionPane.ERROR_MESSAGE);
                    Toolkit.getDefaultToolkit().beep();
                }
            }                                               
        }
    }

} // end class
于 2012-02-26T08:51:31.830 に答える