2011-12-26 52 views
5

我正在嘗試使用值爲0.0005,最小= 0.0,最大= 1.0,步長= 0.0005的SpinnerNumberModel來設置JSpinner。然而,當我用這些參數創建一個微調器時,我觀察到非常奇怪的行爲。而不是在0.0005開始,並且每次點擊向上箭頭時增加0.0005,該值似乎堅持在0.Java中的奇數SpinnerNumberModel行爲

爲了確保這不僅僅是一個格式問題,我打印出微調後的值每個改變事件。毫無疑問,對於向上箭頭的每次點擊,控制檯顯示值爲0,然後顯示0.0005,無論微調控制器點擊了多少次。

下面是我用來測試它的代碼,其中包括一個微調值稍微不同的微調器,可以用於比較目的。

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

public class Main { 

    public static void main(String[] args) { 
     JFrame frame = new JFrame(); 
     frame.setSize(200, 80); 
     JPanel panel = new JPanel(); 
     panel.setLayout(new BorderLayout()); 
     final JSpinner spinner1 = new JSpinner(new SpinnerNumberModel(0.0005, 0.0, 1.0, 0.0005)); 
     final JSpinner spinner2 = new JSpinner(new SpinnerNumberModel(0.05, 0.0, 1.0, 0.05)); 
     panel.add(spinner1, BorderLayout.NORTH); 
     panel.add(spinner2, BorderLayout.SOUTH); 
     frame.add(panel); 
     spinner1.addChangeListener(new ChangeListener() { 
      public void stateChanged(ChangeEvent e) { 
       System.out.println("spinner1: " + ((Number) spinner1.getValue()).doubleValue()); 
      } 
     }); 
     spinner2.addChangeListener(new ChangeListener() { 
      public void stateChanged(ChangeEvent e) { 
       System.out.println("spinner2: " + ((Number) spinner2.getValue()).doubleValue()); 
      } 
     }); 
     frame.setVisible(true); 
     frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
    } 

} 

任何人都可以向我解釋爲什麼spinner2按預期工作,但spinner1不?

謝謝。

編輯:感謝Peter指出微調器文本字段的格式實際上對存儲值有影響。爲了讓第一個微調按預期工作,我添加了一行:spinner1.setEditor(new JSpinner.NumberEditor(spinner1, "0.0000"));

+0

感謝您的輸入。我第一次遇到這個問題的實際項目比這個複雜得多。我在這裏發佈的代碼是展示該問題的一個非常簡單的例子。 – 2011-12-26 09:13:40

+0

好的,我編輯了這個例子來包含一個JPanel來保存兩個spinners。不幸的是,我仍然對第一個微調者獲得了同樣不可思議的結果。 – 2011-12-26 09:23:12

+0

我已經使用JPanel,問題依然存在。我已經嘗試使用(0.001,0.0001)作爲JSpinner模型的(值,步)和(0.0001,0.001)。兩者都不起作用。但是(0.001,0.001)代替。這是否意味着JSpinner的準確性問題? – xorange 2011-12-26 09:26:01

回答

9

問題出在微調器使用的JFormattedTextField中。 在該編輯器,你可以找到:

public void commitEdit() throws ParseException { 
    AbstractFormatter format = getFormatter(); 

    if (format != null) { 
     setValue(format.stringToValue(getText()), false, true); 
    } 
} 

您微調顯示0.0005爲0.0,如果你增加它首先把0.0在您的模型,然後遞增到0.0005,則事件實際上捕捉它,但你的文本框只能看到0.0

所以解決方法是更改​​微調器文本字段的格式。

您可以在此改變編輯

final JSpinner spinner1 = new JSpinner(new SpinnerNumberModel(0.0005, 0.0, 1.0, 0.0005)) { 
     @Override 
     protected JComponent createEditor(SpinnerModel model) 
     { 
     return new NumberEditor(this, "0.0000");//needed decimal format 
     } 
    }; 
+0

有意思......我假設微調器保持相同的雙精度值,不管它是如何被文本字段格式化的。謝謝! – 2011-12-26 09:31:34

+0

謝謝彼得。我編輯了我的問題,以包含一個用於類似目的的附加行。 – 2011-12-26 09:39:36