0

我有一个具有 65536 个不同值的 JSlider。它适用于粗调和非常精细的调整(使用向上/向下箭头+/-1),但在中间非常差。

那里有什么更好的吗?我可以模糊地想象将 2 个滑块用于粗调 + 微调,但无法真正弄清楚如何让它们一起工作。

4

1 回答 1

1

使用 aJSpinner而不是 aJSlider怎么样?使用 a SpinnerNumberModel,您可以设置步长,甚至可以动态更改步长。

如果您对拥有多个控件感到满意,您甚至可以有两个微调器,一个用于设置您的值,另一个用于设置第一个微调器使用的步长。

例如,我从Swing 滑块教程中获取 SliderDemo代码,并将其修改为使用两个而不是单个. 这是我更改的代码中最有趣的部分:JSpinnersJSlider

//Create the slider^H^H^H^H^H^H spinners.
// JSlider framesPerSecond = new JSlider(JSlider.HORIZONTAL,
//                                       FPS_MIN, FPS_MAX, FPS_INIT);
final int initStep = 1;
final SpinnerNumberModel animationModel = new SpinnerNumberModel(FPS_INIT,
                                                                 FPS_MIN,
                                                                 FPS_MAX,
                                                                 initStep);
final SpinnerNumberModel stepSizeModel = new SpinnerNumberModel(initStep,
                                                                1,
                                                                10,
                                                                1);
final JSpinner framesSpinner = new JSpinner(animationModel);
framesSpinner.addChangeListener(this);

final JSpinner stepSpinner = new JSpinner(stepSizeModel);
stepSpinner.addChangeListener(new ChangeListener() 
{
    public void stateChanged(ChangeEvent arg0)
    {
        animationModel.setStepSize(stepSizeModel.getNumber());
    } 
});

我还必须进行一些不那么有趣的更改,例如为步长微调器创建一个标签,将新标签和新微调器添加到容器中,以及更改stateChanged()方法 onthis以将事件源转换为 aJSpinner而不是将其转换为JSlider.

当然,您可以进一步详细说明这一点,例如增加步长微调器的步长(例如,您可以通过单击将步长从 1 更改为 101)。您还可以使用不同的控件而不是 aJSpinner来设置步长,例如组合框。

最后,为了使这一切真正易于使用,您可能想要连接一些按键加速器(可能通过菜单?),这样您就可以更改步长,而无需实际将鼠标或键盘焦点从一个微调器移动到另一个微调器.

编辑:鉴于无论如何您都必须使用 a ,您是否知道您可以使用 PgUp/ PgDnJSlider上下移动总范围的 1/10?

如果您想更改 1/10 的数量(例如使其成为动态),那么您需要覆盖 method BasicSliderUI.scrollByBlock()

这是一个示例,我只是将 a 的 UI 类覆盖JSlider到范围的 1/4 th,而不是 1/10 th

//Create the slider.
JSlider framesPerSecond = new JSlider(JSlider.HORIZONTAL,
                                      FPS_MIN, FPS_MAX, FPS_INIT);
framesPerSecond.setUI(new javax.swing.plaf.metal.MetalSliderUI() {

    private static final int SLIDER_FRACTION = 4;

    /**
     * This code is cut, paste, and modified from
     * {@link javax.swing.plaf.basic.BasicSliderUI#scrollByBlock(int).
     * I should be ashamed of cutting and pasting, but whoever hardcoded the magic
     * number "10" in the original code should be more ashamed than me. ;-) 
     *
     * @param direction
     *          either +1 or -1
     */   
    @Override
    public void scrollByBlock(final int direction) {
        synchronized(slider)    {
            int oldValue = slider.getValue();
            int blockIncrement = (slider.getMaximum() - slider.getMinimum()) / SLIDER_FRACTION;
            if (blockIncrement <= 0 && slider.getMaximum() > slider.getMinimum()) {
                blockIncrement = 1;
            }
            int delta = blockIncrement * ((direction > 0) ? POSITIVE_SCROLL : NEGATIVE_SCROLL);
            slider.setValue(oldValue + delta);          
        }
    }
});

SLIDER_FRACTION从这里开始,用另一个滑块或微调器设置的变量替换该常量不会太难,不是吗?

于 2010-02-28T14:35:36.337 回答