0

The situation here is the following: I have a JFrame, in which I store a list of images. When the right-key is pressed, I display the next image in this fullscreen JFrame. I want a Exit JButton in the upper right corner of the screen, which is the problem. To achieve that, I create a new JPanel everytime the image is changed, remove the old JPanel from the frame, and add the JButton to the new JPanel. The issue is the following: when I start the program, the JButton is in the middle of the JFrame. Once I load the next Image by pressing the right key the JButton is on the right position. However, workarounds like calling the method to display the next Image fail. Even if I set the JButton invisible until the right key was pressed and the second image loaded, it still will be in the center of the screen instead of the upper right. The following code is used:

BufferedImage image = ImageIO.read(images.get(number));
JPanel panel = new JPanel() {
    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        g.drawImage(image, 0, 0, null);
    }
};
if (currentPanel != null) {
    this.remove(currentPanel);
}
panel.setSize(Gallery.this.getSize());
currentPanel = this.add(panel);
jButton1.setBounds(Gallery.this.getWidth() - jButton1.getWidth(), 0, jButton1.getWidth(), jButton1.getHeight());
panel.add(jButton1);
currentPanel.repaint();

This code is executed once at startup. The JButton then is in the middle. It is executed again when loading the next Image, JButton now is in correct position.

I already tried many things, like adding the JButton to the JFrame instead, setting JPanels layout to null (makes button invisible), repaint, pack, invalidate, nothing I try seems to work. Is anyone able to instruct Swing to place that JButton in the upper right corner of my JFrame? Thank you a lot!

Andrew Thompson
  • 168,117
  • 40
  • 217
  • 433
Zackline
  • 804
  • 1
  • 9
  • 28
  • 2
    Put a `JLabel` (inside a `JScrollPane`) inside a `JPanel` with `GridBagLayout`. Create a second panel with `FlowLayout` (using the `FlowLayout.TRAILING` for right alignment) and add the button to it. Create a 3rd panel with `BorderLayout`. Add the button panel to the `PAGE_START` and the label panel to the `CENTER`. When changing images, don't remove or add anything, just change the icon of the label. – Andrew Thompson Apr 10 '15 at 18:48
  • 2
    1) For better help sooner, post an [MCVE](http://stackoverflow.com/help/mcve) (Minimal Complete Verifiable Example) or [SSCCE](http://www.sscce.org/) (Short, Self Contained, Correct Example). 2) One way to get image(s) for an example is to hot link to images seen in [this Q&A](http://stackoverflow.com/q/19209650/418556). 3) `g.drawImage(image, 0, 0, null);` should be `g.drawImage(image, 0, 0, this);` – Andrew Thompson Apr 10 '15 at 18:49
  • @AndrewThompson Thank you, I will try to include a compileable example in future questions. Your solution sounds very complicated to me, would be a shame if such a easy task would require so many components and different layouts. I'll consider drawing an image instead of the button to avoid messing with Swing. Thank you anyway. – Zackline Apr 10 '15 at 20:31

1 Answers1

0

After cleaning up the mess I programmed there, an easy solution proved to work: I added a custom JPanel to the JFrame at startup and set a fixed width to the JButton. Here the JPanel:

public class ImagePanel extends javax.swing.JPanel {
Image image;

public Image getImage() {
    return image;
}

public void setImage(Image image) {
    this.image = image;
}

public ImagePanel() {
    initComponents();
}

@Override
protected void paintComponent(Graphics g) {
    super.paintComponent(g);
    g.drawImage(image, 0, 0, this);
}                  

}

I set a fixed width to the JButton and added it to that JPanel:

    jButton1 = new JButton();
    jButton1.setText("Exit");
    imagePanel = new ImagePanel();
    imagePanel.setSize(Gallery.this.getSize());
    add(imagePanel);
    imagePanel.add(jButton1);
    jButton1.setBounds(Gallery.this.getWidth() - 50, 0, 50, 30);
    jButton1.addActionListener((ActionEvent e) -> exit());
    displayImage(0);

The displayImage method consists of these lines:

 BufferedImage image = ImageIO.read(images.get(number));
 imagePanel.setImage(image);
 imagePanel.repaint();
Zackline
  • 804
  • 1
  • 9
  • 28