Ive got a JFrame and set the LayoutManager to BorderLayout and then proceeded to add my JLabel with an image. However when i resize the frame the JLabel doesnt resize. I have not added any components to North, S, E and so on. I was hoping to simply have the image inside the label fill up the entire frame leaving my menu in tact of course.
-
I hope that the image in question is big enough, to occupy the space. Please, have a look at this [example](http://stackoverflow.com/a/11372350/1057230) – nIcE cOw Jul 28 '12 at 04:45
-
Yes the image is reasonably large enough, its not a tiny icon or anything. – mP. Jul 28 '12 at 04:56
-
1Label's don't resize the icons ;) – MadProgrammer Jul 28 '12 at 05:14
2 Answers
Forgive me if this seems arrogant, but I have nothing else to go on.
I did a quick sample
See the red line around the image, that's the JLabel
's border. As you can see, the label is been re-sized to fill the entire area.
This is the code I used to produce the sample
public class LayoutFrame extends JFrame {
public LayoutFrame() throws HeadlessException {
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
Image image = null;
URL url = getClass().getResource("/layout/issue78.jpg");
try {
image = ImageIO.read(url);
} catch (IOException ex) {
ex.printStackTrace();
}
JLabel label = new JLabel(new ImageIcon(image));
label.setHorizontalAlignment(JLabel.CENTER);
label.setVerticalAlignment(JLabel.CENTER);
label.setBorder(new LineBorder(Color.RED, 4));
setLayout(new BorderLayout());
add(label);
}
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException ex) {
} catch (InstantiationException ex) {
} catch (IllegalAccessException ex) {
} catch (UnsupportedLookAndFeelException ex) {
}
LayoutFrame frame = new LayoutFrame();
frame.setSize(200, 200);
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
});
}
}
Obviously, you'll need to supply your own image ;).
Don't forget, the label WON'T scale the content for you, if that's your goal, you'll need to implement your own component to achieve this.
If you're still having problems, I would suggest (in the absence of further evidence) that your label may not be in the container you think it is or the containers layout manager is not what you think it is.
UPDATE
I don't know why you're having issues with components going missing or issues with you menu. Are mixing heavy and light weight components??
Sample with menu bar
After reading your question a little closer, I've devised a simple resizing image pane sample. For speed, I've relied on my libraries, but it should be reasonably easy to implementation your own code in place of my calls
public class ImagePane extends JPanel {
protected static final Object RESIZE_LOCK = new Object();
private BufferedImage image;
private BufferedImage scaledImage;
private Timer resizeTimer;
public ImagePane() {
URL url = getClass().getResource("/layout/issue78.jpg");
try {
image = ImageIO.read(url);
} catch (IOException ex) {
ex.printStackTrace();
}
resizeTimer = new Timer(250, new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
// Simple thread factory to start a slightly lower
// priority thread.
CoreThreadFactory.getUIInstance().execute(new ResizeTask());
}
});
resizeTimer.setCoalesce(true);
resizeTimer.setRepeats(false);
}
@Override
public void setBounds(int x, int y, int width, int height) {
super.setBounds(x, y, width, height);
resizeTimer.restart();
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g;
if (scaledImage != null) {
// This simply returns a rectangle that takes into consideration
//the containers insets
Rectangle safeBounds = UIUtilities.getSafeBounds(this);
System.out.println("scaledImage = " + scaledImage.getWidth() + "x" + scaledImage.getWidth());
int x = ((safeBounds.width - scaledImage.getWidth()) / 2) + safeBounds.x;
int y = ((safeBounds.height - scaledImage.getHeight()) / 2) + safeBounds.y;
g2d.drawImage(scaledImage, x, y, this);
}
}
protected class ResizeTask implements Runnable {
@Override
public void run() {
synchronized (RESIZE_LOCK) {
if (image != null) {
int width = getWidth();
int height = getHeight();
System.out.println("width = " + width);
System.out.println("height = " + height);
// A simple divide and conquer resize implementation
// this will scale the image so that it will fit within
// the supplied bounds
scaledImage = ImageUtilities.getScaledInstanceToFit(image, new Dimension(width, height), ImageUtilities.RenderQuality.High);
System.out.println("scaledImage = " + scaledImage.getWidth() + "x" + scaledImage.getWidth());
repaint(); // this is one of the few thread safe calls
}
}
}
}
}

- 343,457
- 22
- 230
- 366
-
thanx for the sample. The problem with it is that it takes over everything and other components are lost, like a menu. You are correct, my problem is the label is not resizing the iconimage inside it which part of the pain. – mP. Jul 28 '12 at 05:31
-
-
@trashgod without knowing the level of knowledge of the OP, I didn't want to sound condescending but I had no idea what had been tried so I had no choice but to start at basics :P – MadProgrammer Jul 28 '12 at 22:46
Best option is to sub class ImageIcon and override its paintIcon method to simply paint the image using the Graphics.paint( x, y, width, height ...).

- 18,002
- 10
- 71
- 105
-
1arguably an illegal implementation of icon: getIconWidth/Height is doc'ed to return _an int specifying the **fixed** width of the icon_ - that's not possible with resizing on the fly ... – kleopatra Jul 28 '12 at 09:17
-
IMHO I think you'd better of with some kind of `Factory` that could take the base line `Icon` and either produce a new `Icon` of the required size or paint one on your behalf. You, however, run the risk of "stalling" the `EDT` if the scaling operation is considerable (say scaling down to 0.1% or over several 100% - depending on the size of the original image). As my example shows, it uses a "coalesce" approach to the resize request, rather then resizing on EVERY request, we try and resize on as few requests as possible, usually when we reach a "idle" state. But that's just MHO – MadProgrammer Jul 28 '12 at 22:51
-
@madProgrammer sorry for badly wording the original q, i dont want to resize the image within the icon. I only want the image to be stretched to fill the parent component. I know this bad wording probably screwed up your response, but i hope it addresses why i tried what i did. – mP. Jul 29 '12 at 14:13
-
@mP okay, so is stretching not resizing? Does tat Evan you don't care about maintaining the aspect ratio – MadProgrammer Jul 29 '12 at 19:12