简体   繁体   English

Java Swing - 无法将滚动条添加到我的面板

[英]Java Swing - Cant add scrollbar to my panel

Im trying to create a small client where I can paint coordinates onto a map.我正在尝试创建一个小型客户端,我可以在其中将坐标绘制到地图上。 I want to start by loading a map image on to a JPanel and then add that panel to a frame.我想首先将地图图像加载到 JPanel,然后将该面板添加到框架中。 The image is very large hence you need to be able to scroll to see all of it.图像非常大,因此您需要能够滚动才能看到所有图像。

But for some reason my scroll bar wont show up.但由于某种原因,我的滚动条不会出现。 I tried most guides but it wont work.我尝试了大多数指南,但它不起作用。

here is my panel class:这是我的面板类:

public class MapPanel extends JPanel implements Pointable {

    private static final long serialVersionUID = 1L;
    private List<Shape> shapes = new LinkedList<>();


    public MapPanel() {
        Commander.getInstance().addShapeContainer(this);
        shapeContainerState = NoState.getInstance();
        MouseHandler mouseHandler = new MouseHandler(this);
        KeyListener keyListener = new KeyListener();

        this.addMouseListener(mouseHandler);
        this.addMouseMotionListener(mouseHandler);
        this.addKeyListener(keyListener);
        this.setBackground(Color.white);
        this.setFocusable(true);
        this.requestFocusInWindow();
    }

    public void paintComponent(Graphics g) {
        super.paintComponent(g);

        BufferedImage image;
        try {
            image = ImageIO.read(new File("earthmap1.jpg"));
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

        g.drawImage(image, 0, 0, null);
}

And here is my JFrame class:这是我的 JFrame 类:

public class MapFrame extends JFrame {

 public MapFrame() {
        buildTheUI();
        setUpEventHandling();
        mapPanel = new MapPanel();

        JScrollPane scrollPane = new JScrollPane(mapPanel);
        scrollPane.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
        scrollPane.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED);

        this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        this.setSize(900, 800);
        this.add(scrollPane);
        this.setVisible(true);
    }
}

The image is displayed fine and if i enlarge the window u can see more of it (as all of it is not displayed) but there are no scroll bars so i can see the rest of the image by scrolling.图像显示良好,如果我放大窗口,您可以看到更多内容(因为所有内容都没有显示),但没有滚动条,所以我可以通过滚动查看图像的其余部分。 在此处输入图像描述

Your problem is due to the JPanel's preferred size -- it needs to match the size of the image.您的问题是由于 JPanel 的首选尺寸 - 它需要与图像的尺寸相匹配。 I recommend overriding the public Dimension getPreferredSize() method and return a dimension that matches the size of the image.我建议覆盖public Dimension getPreferredSize()方法并返回与图像大小匹配的维度。

Side issue: Do not read in an image in a painting method such as paintComponent.附带问题:不要在诸如paintComponent之类的绘画方法中读入图像。 These methods help determine the perceived responsiveness of your program and need to be as fast as possible.这些方法有助于确定程序的感知响应能力,并且需要尽可能快。 What is more, there is no reason to re-read the image in each time the JPanel gets a repaint, and instead read the image in once, say in the class's constructor.更重要的是,没有理由在每次 JPanel 重新绘制时重新读取图像,而是读取一次图像,例如在类的构造函数中。

eg,例如,

public class MapPanel extends JPanel implements Pointable {

    private static final long serialVersionUID = 1L;
    private List<Shape> shapes = new LinkedList<>();
    private BufferedImage image = null;


    public MapPanel() throws IOException {
        Commander.getInstance().addShapeContainer(this);
        shapeContainerState = NoState.getInstance();
        MouseHandler mouseHandler = new MouseHandler(this);
        KeyListener keyListener = new KeyListener();

        this.addMouseListener(mouseHandler);
        this.addMouseMotionListener(mouseHandler);
        this.addKeyListener(keyListener);
        this.setBackground(Color.white);
        this.setFocusable(true);
        this.requestFocusInWindow();
        
        image = ImageIO.read(new File("earthmap1.jpg"));
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);

        if (image != null) {
            g.drawImage(image, 0, 0, null);
        }
    }
        
    @Override
    public Dimension getPreferredSize() {
        if (image == null) {
            return super.getPreferredSize();
        } else {
            int w = image.getWidth();
            int h = image.getHeight();
            return new Dimension(w, h);
        }
    }
    
}

Note: code has not been tested注意:代码未经测试

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM