滚动后JLabel消失了

时间:2014-02-17 15:49:33

标签: java swing layout jscrollpane jlabel

我的滚动面板包含ImageIcon。我想在px中添加JLabel绝对位置。我得到了什么:Swing app image

代码:

public class HelloWorld {


    HelloWorld() {

        JFrame jfrm = new JFrame("Hello, World!");
        jfrm.setSize(640, 480);
        JPanel mapPanel = new JPanel();
        mapPanel.setLayout(null);
        mapPanel.setSize(600,400);
        jfrm.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        ImageIcon imageIcon = new ImageIcon("src\\SwingExp\\img\\map.gif");
        JScrollPane scrollPane = new JScrollPane(new JLabel(imageIcon));
        scrollPane.setBounds(5,5,600,400);
        JLabel usaLabel = new JLabel("U.S.A.");
        usaLabel.setBounds(210,200,50,25);
        mapPanel.add(usaLabel);
        mapPanel.add(scrollPane);

        jfrm.add(mapPanel);
        jfrm.setVisible(true);
    }

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                new HelloWorld();
            }
        });
    }
}

但如果我滚动一点,美国标签将从地图中消失: Swing app image

正如您所见,

JLabel职位必须是绝对的。怎么避免这个?

2 个答案:

答案 0 :(得分:3)

usaLabel添加到包含图标的标签,而不是滚动窗格:

ImageIcon imageIcon = new ImageIcon("src\\SwingExp\\img\\map.gif");
JLabel map = new JLabel( imageIcon );
JScrollPane scrollPane = new JScrollPane( map );
//JScrollPane scrollPane = new JScrollPane(new JLabel(imageIcon));
scrollPane.setBounds(5,5,600,400);
JLabel usaLabel = new JLabel("U.S.A.");
usaLabel.setBounds(210,200,50,25);
map.add( usaLabel );
//mapPanel.add(usaLabel);

也到处停止使用null布局。您不需要mapPanel变量。只需将滚动窗格直接添加到框架的内容窗格即可。默认情况下,滚动窗格将添加到CENTER中,并占用框架中的所有可用空间。

答案 1 :(得分:2)

我提供这个作为替代答案:

  • 它使用EmptyBorder表示白色(OK蓝色)空间
  • 滚动窗格返回按宽度系数缩放的首选大小。
  • 滚动到最后然后无缝地重新开始。
  • 美国(澳大利亚,新西兰及其他地方描绘的)总是在视野中,因为GUI显示一个'图像宽度'。 ;)

screen shot of world image scrolling in option pane

源图像是为this answer创建的。

  

world source image

代码

import java.awt.*;
import java.awt.event.*;
import java.awt.image.BufferedImage;
import javax.swing.*;
import javax.swing.border.EmptyBorder;
import java.net.*;
import javax.imageio.ImageIO;

class HelloScrollingWorld {

    public JPanel gui = new JPanel(new BorderLayout());
    JScrollPane scrollPane;
    Timer timer = null;
    /**
     * The number of images we tile horizontally, must be >1 for scroll bar
     */
    int width = 2;
    /**
     * The equator (drawn in pale gray) is 44 px south of the vertical
     * center of the image.
     */
    int offset = 44;
    /**
     * Use this as padding on top and bottom.
     */
    int pad = 15;

    HelloScrollingWorld() {
        try {
            URL worldImage = new URL("http://i.stack.imgur.com/OEGTq.png");
            BufferedImage img = ImageIO.read(worldImage);
            initComponents(img);
        } catch (Exception ex) {
            ex.printStackTrace();
        }
    }

    private final void initComponents(final BufferedImage image) {
        JPanel multiimage = new JPanel(new GridLayout(1, 0, 0, 0));
        for (int ii = 0; ii < width; ii++) {
            multiimage.add(new JLabel(new ImageIcon(image)));
        }
        multiimage.setBackground(Color.BLUE.brighter());
        // add the white (or bright blue) space.
        multiimage.setBorder(new EmptyBorder(pad, 0, pad + offset, 0));
        scrollPane = new JScrollPane(
                multiimage,
                JScrollPane.VERTICAL_SCROLLBAR_NEVER,
                JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS) {

            /**
             * return the preferred size scaled by the width.
             */
            @Override
            public Dimension getPreferredSize() {
                Dimension d = super.getPreferredSize();

                return new Dimension(d.width / width, d.height);
            }
        };
        gui.add(scrollPane, BorderLayout.CENTER);
        ActionListener scrollListener = new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                scrollGui();
            }
        };
        timer = new Timer(15, scrollListener);
        timer.start();
    }

    public void stopTimer() {
        timer.stop();
    }

    public void scrollGui() {
        JScrollBar scrollBar = scrollPane.getHorizontalScrollBar();
        BoundedRangeModel model = scrollBar.getModel();
        int max = model.getMaximum() - scrollBar.getVisibleAmount();
        int now = model.getValue();
        if (now < max) {
            model.setValue(now + 1);
        } else {
            model.setValue(1);
        }
    }

    public JComponent getGui() {
        return gui;
    }

    public static void main(String[] args) {
        Runnable r = new Runnable() {

            @Override
            public void run() {
                HelloScrollingWorld hsw = new HelloScrollingWorld();

                JOptionPane.showMessageDialog(
                        null,
                        hsw.getGui(),
                        "Hello Scrolling Padded World",
                        JOptionPane.INFORMATION_MESSAGE);

                hsw.stopTimer();
            }
        };
        // Swing GUIs should be created and updated on the EDT
        // http://docs.oracle.com/javase/tutorial/uiswing/concurrency
        SwingUtilities.invokeLater(r);
    }
}