Dynamically resize images linked to JLabels in a GridLayout layoutmanager - java

Current implementation layout:
((EDIT: added
Code: ))
private JPanel panelCenter;
private List<BufferedImage> listCreatedImages;
public ChooseCircuitPanel(List<BufferedImage> listCreatedImages) {
this.listCreatedImages = listCreatedImages;
initiate();
}
private void initiate() {
setLayout(new BorderLayout(50, 50));
panelCenter = new JPanel();
LayoutManager theLayout = new GridLayout(0, 3, 0, 0);
panelCenter.setLayout(theLayout);
panelCenter.setBorder(BorderFactory.createLineBorder(Color.BLACK));
for (BufferedImage bufferedImage : listCreatedImages) {
ImageIcon theImage = new ImageIcon(bufferedImage);
JLabel lblForImage = new JLabel(theImage);
lblForImage.setBorder(BorderFactory.createLineBorder(Color.BLACK));
panelCenter.add(lblForImage);
}
this.add(panelCenter, BorderLayout.CENTER);
}
Situation:
We want to display a race circuit here. A circuit should be displayed by placing standards tiles next to each other. It should be possible to resize the window, and with that, the circuit tiles should also resize.
((EDIT: bit more info: The race circuit data is stored on a server and the desktop application has to translate the data to a visual thing, by placing some standard tiles in the right order. ))
((EDIT: we are not allowed to use any external library. It should be doable by only using Java Swing code.))
I thought about placing the images in a JLabel and placing these JLabels in a panel with GridLayout as layout manager.
Using a GridLayout - I thought - it should be rather easy to get to a solution:
the components in the GridLayout (= JLabels) already scale and do exactly what I want.
Now, it would only be a matter of finding a way to resize the images so they fill the JLabels.
As you can see: right now, the images have a fixed size and don't scale at all.
I browsed a bit and saw lots of solutions that boil down to using Graphics2D and super.paintComponent, etc.
But most of these solutions had nothing to do with a GridLayout.
So conclusive question:
Is there an easier solution aside from using Graphics2D, etc. knowing that I use a GridLayout?
If not, I will of course use Graphics2D, etc. but I'm now just exploring my options. :)
((EDIT: SOLVED The tiles now neatly fit on each other. Don't mind the misalignments, that's our fault.))

There are no Swing components that do what you want so you will need to write your own code.
The easiest approach would be to use Darryl's Stretch Icon on your JLabel.
Or another approach is to create your own custom component that dynamically scales the image as it is painted. Something like the Background Panel which has code that allows you to scale or tile an image.

Given the nature of the view, I would recommend abandoning images altogether and instead implement the rendering in an Icon. Presuming you can make an icon scale with the label.

Related

Java JPanel Layout

Im new in Java Swing, and want to make my layout, but can't do this
Look Now :
Look I want :
Code Now :
JPanel MainPanel = new JPanel(new GridBagLayout());
JLabel MoneyLabel = new JLabel(MoneyIcon);
MoneyLabel.setHorizontalTextPosition(JLabel.CENTER);
MoneyLabel.setVerticalTextPosition(JLabel.BOTTOM);
MoneyLabel.setText("Money:" + CarMain.Money);
JLabel MoneyClicksLabel = new JLabel();
MoneyClicksLabel.setHorizontalTextPosition(JLabel.CENTER);
MoneyClicksLabel.setVerticalTextPosition(JLabel.BOTTOM);
MoneyClicksLabel.setText("Money Clicks: " + CarMain.MoneyClicks);
JLabel BoxesLabel = new JLabel(BoxLv9_10Icon);
BoxesLabel.setHorizontalTextPosition(JLabel.CENTER);
BoxesLabel.setVerticalTextPosition(JLabel.BOTTOM);
BoxesLabel.setText("Boxes: " + CarMain.Boxes);
JLabel BoxesClicksLabel = new JLabel();
BoxesClicksLabel.setHorizontalTextPosition(JLabel.CENTER);
BoxesClicksLabel.setVerticalTextPosition(JLabel.BOTTOM);
BoxesClicksLabel.setText("Boxes Clicks: " + CarMain.BoxesClicks);
MainPanel.add(MoneyLabel);
MainPanel.add(MoneyClicksLabel);
MainPanel.add(jbtnMoney);
MainPanel.add(BoxesLabel);
MainPanel.add(BoxesClicksLabel);
MainPanel.add(jbtnBoxes);
This is simple example of, what i want, becouse i'm building ingame shop, with 13 labels like these, in each tabbedpane window. How can i make it look, like in second picture, what I want?
Im new in Java Swing, and want to make my layout, but can't do this
Probably no single layout can suit everyone's needs. But combining several layouts can usually handle most scenarios.
From the image you showed in the question. There is no need to write your own layout. You can always use sub panels to hold your components and set a specific layout for each sub panel to handle what you need for those individual areas.
The reason for the alignment in your first attached image is because:
JPanel uses FlowLayout as its default layout. Hence all the components added will appear in a linear fashion and tries to fill up the row as much as possible the panel's width can hold. Once exceeded the panel's width, the components will be pushed to the next row.
If you want to achieve the alignment in the second attached image:
You may create a main panel to contain several sub-panels (see image below).
The red box is your main panel and you may continue to use the default FlowLayout.
Then add your components into sub-panels (orange boxes) before adding it to the main. You may then use BoxLayout, FlowLayout or even GridBagLayout for the sub panels (orange boxes).
Artis Uljanovs, at night after work i will give a look at this to help you.
I recommend you already to read the following: https://docs.oracle.com/javase/tutorial/uiswing/layout/visual.html
You need some foundations on Java Layouts.

Displaying Overlapping BufferedImages in Java

I was wondering if anyone knows how to display multiple (probably just 2) BufferedImages overlapping each other; in other words, using BufferedImage.TYPE_INT_ARGB for the top image I want to be able to superimpose one image above the other, while still being able to view the lower image depending on alpha values.
The way I am familiar with displaying them is as an ImageIcon attached to a JLabel, ie:
JLabel myLabel = new JLabel("");
myLabel.setIcon(new ImageIcon(myBufferedImage));
As far as I know, this method doesn't seem conducive to layering BufferedImages over one another and so I am looking for an alternative method of doing this.
Alternatively if you know a way I could layer the images (without drawing one to the other) while still using the ImageIcon that would be great as well.
As far as I know, this method doesn't seem conducive to layering BufferedImages over one another and so I am looking for an alternative method of doing this.
You can add any component to a JLabel, so you could add a second label to the first label:
JLabel topLabel = new JLabel(...);
topLabel.setSize( topLabel.getPreferredSize();
topLabel.setLocation(10, 10);
myLabel.add( topLabel );
Or maybe a better approach is to use a JLayeredPane which allows you to stack multiple components on top of one another. Read the section from the Swing tutorial on How to Use Layered Panes for a working example.

Placing border in desire location inside JPanel

I am trying to put a border around the buttons inside of my JPanel. I have this:
Border lineBorder = BorderFactory.createLineBorder(Color.black);
welcomePanel.setBorder(lineBorder);
But that only puts the border around my entire application window, which makes sense. I am wanting to be able to place the border where I want.... I did this when placing my buttons in the desired location
button1.setBounds(10, 10, 60, 30);
And I looked in the API and saw a paintBorder method with parameters of int x, int y, int width, int height, which would make sense to me, but I couldn't get it to work.
Any advicewould be appreciated
Start by adding you buttons to another JPanel...
JPanel buttons = new JPanel();
buttons.setLayout(...);
// add buttons...
Set the Border of this panel...
buttons.setBorder(BorderFactory.createLineBorder(Color.black));
Add this to you main container...
welcomePanel.add(buttons);
Pixel perfect layouts are an illusion in modern UI design, you don't control factors like font choices, rendering pipelines, DPI and other factors which will change the requirements needed for each component to be positioned, that is the role of layout managers.
Swing has been designed to work with layout managers, attempting to do without will cause no end of issues and frustration as you try and find more hacks to get around the issues.
You can use things like EmptyBorders to introduce empty space between components or Insets with a GridBagLayout

jpanel with image in background

I have a simple doubt, I need to replace this:
panel[1].setBackground(Color.red);
For an image, but I want to avoid a new jlabel for image, because I tested and I have another label inside this panel that is pushed to below
Background Panel shows two approaches. One involves custom painting, the other involves using a JLabel. The approach you use will be based on your requirement. The custom painting is more flexible but a little more complicated.

Can I create a JFrame with multiple images?

Here is my problem:
I have an application that every iteration it returns to me a list of images. The imagens have different sizes and the number of images to be shown varies every time.
Is there a way to show in a jFrame all the images without knowing the number of jPanels to create? Is there an easy way to do that?
Obs.: The images should be shown at same time, like side by side, or listed, because they are used for comparisson purposes.
Obs.2: The number of images to be shown is around 20-60 for each time.
Thanks
As you want to see all your images in the same Panel, I suggest you use a TreeMap Algorithm to display your panels using the dimension of your image as the weight of each image. And then, resize each image so it can fit in each panel.
(source: tumblr.com)
See a Java implementation here: http://plindenbaum.blogspot.com/2009/08/treemap-for-friendfeed.html
this solution should work:
class MyFrame extends JFrame
{
MyFrame(Image images[])
{
JTabbedPane tabbed= new JTabbedPane();
setContentPane(tabbed);
for(int i=0;i< images.length;++i)
{
tabbed.addTab("Image "+i, new JScrollPane(new JLabel(new ImageIcon(images[i]))));
}
}
If you use JInternalFrame for this, you can drag the pictures around and change the size, too.
From your question I assume that you are able to show images in a JPanel. In that case, you can keep a list of JPanels and dynamically update this list. Of course, the layout to be drawn on the JFrame is completely up to you, but for a job like this one, you might want to use GridLayout or BoxLayout.
To keep a list of JPanels:
ArrayList<JPanel> panelList = new ArrayList<JPanel>();
...
panelList.add(new JPanel());
...
panelList.clear();

Categories

Resources