自定义JScrollBar-Thumb已绘制,但不移动

时间:2012-05-05 14:55:24

标签: swing slider thumbnails jscrollbar

我决定在摇摆和定制绘画组件的材料中潜水一点点。 最近几天,我在StackOverFlow和其他论坛上阅读了大量文章,API文档和问题。但是在理解这个概念时我仍然遇到了一些基本问题。

我想做什么:基本上,我想为自己的Swing GUI设计一些组件。我在设计自定义JButton时没有太多问题。我只是在paint.net中创建一个自定义Image,创建一个ImageIcon并生成JButton.setIcon(ImageIcon),它工作正常。如果我想自定义JSlider的Thumb,也是如此。我在这里找到了一个非常有趣的解它只是覆盖了default-thumb而没有任何东西,在第二步中它将一个自定义ImageIcon(通过ClassLoader使用我的自定义createImageIcon-class)放到UIManger的“Slider.horizo​​ntalThumbIcon”中。

UIManager.getLookAndFeelDefaults().put("Slider.horizontalThumbIcon", new Icon(){

    public int getIconHeight() {
        return 0;
    }

    public int getIconWidth() {
        return 0;
    }

    public void paintIcon(Component c, Graphics g, int x, int y) {
       //do nothing
    }
});

UIManager.getLookAndFeelDefaults().put("Slider.horizontalThumbIcon", 
                                        createImageIcon("images/slider.png"));

但现在问题开始了。如果我没错,ScrollBar的拇指不是Icon,所以我必须创建一个自己的“CustomScrollBarUI”类,它扩展了BasicScrollBarUI。此外,我不想要任何箭头键。好的,所以我做了以下事情(从这里的一些示例代码再次激励我):

public class CustomScrollBarUI extends BasicScrollBarUI {

    private ImageIcon img;

    protected JButton createZeroButton() {
        JButton button = new JButton("zero button");
        Dimension zeroDim = new Dimension(0,0);
        button.setPreferredSize(zeroDim);
        button.setMinimumSize(zeroDim);
        button.setMaximumSize(zeroDim);
        return button;
    }


    protected JButton createDecreaseButton(int orientation) {
        return createZeroButton();
    }


    protected JButton createIncreaseButton(int orientation) {
        return createZeroButton();
    }


    protected void paintThumb(Graphics g, JComponent c, Rectangle thumbBounds) {
        BufferedImage img = new LoadBackgroundImage("images/slider.png").getImage();
        g.drawImage(img, 0, 0, new Color(255,255,255,0), null);
    }


    protected void setThumbBounds(int x, int y,int width,int height){
          super.setThumbBounds(x, y, 14, 14);
    }


    protected Rectangle getThumbBounds(){
          return new     Rectangle(super.getThumbBounds().x,super.getThumbBounds().y,14,14);
    } 


        protected Dimension getMinimumThumbSize(){
        return new Dimension(14,14);
    }


    protected Dimension getMaximumThumbSize(){
        return new Dimension(14,14);
    }
}

LoadBackGroundImage是一个自己的类,它通过ClassLoader创建一个BufferedImage。滚动条的拇指现在是我的自定义“slider.png”,但它不会移动。如果我向下拖动它,窗格会滚动,但拇指仍然在他的位置。 由于我还没有理解所有的机制,我读到了paintImage方法。在那里你必须提交一个ImageObserver,它的功能我真的不明白。我在网上发现了各种代码示例(就像我一样),但我认为这对于必须移动(并重新绘制)的图像不起作用。我怎么解决这个问题?如果我在paintThumb方法中绘制一个普通图形,它可以正常工作,但是一旦我绘制一个图像,它就不会移动。

我希望有人可以帮助我。提前谢谢。

1 个答案:

答案 0 :(得分:2)

在您的具体情况下 - 您总是在同一位置绘制图像:

protected void paintThumb(Graphics g, JComponent c, Rectangle thumbBounds) {
    BufferedImage img = new LoadBackgroundImage("images/slider.png").getImage();
    g.drawImage(img, 0, 0, new Color(255,255,255,0), null);
}

“0,0”这里是滚动条坐标系中的“x,y”坐标(零位于左上角)。

您在paintThumb方法(Rectangle thumbBounds)中接收指向当前拇指位置的拇指边界 - 只需使用这些值在适当的位置绘制图像。

如果您的拇指图像尺寸不适合收到的thumbBounds,您可以计算其中间点和中心图像。这只是一个例子 - 你可以用你喜欢的任何其他方式做到这一点。

我想补充的是,几乎每个UI中的每个分离的绘制方法都放在同一个坐标系中,因此你总是必须使用收到的坐标/边界/ ...来放置你正在绘制的内容或者计算它靠你自己。