Multiple JPanels completely on top of each other

I am creating a program in which I can draw a map and add different roads to it, etc. I planned to add terrain maps to one jpanel, and roads, etc. On the other, on top of each other. But I can’t get them to work. I do not know how to add several jpanels completely on top of each other and make them all capable of drawing.

+4
source share
2 answers

The main approach to this problem is to use JLayeredPane and something like GridBagLayout .

JLayeredPane will give you better control over the z-depth of various levels, and GridBagLayout will allow you to assemble components as needed.

You can also take a look at OverlayoutLayout , but never using it, I can not comment.

enter image description here

 import java.awt.BorderLayout; import java.awt.Dimension; import java.awt.EventQueue; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.GridBagConstraints; import java.awt.GridBagLayout; import java.awt.Image; import java.awt.image.BufferedImage; import java.io.File; import java.io.IOException; import java.util.logging.Level; import java.util.logging.Logger; import javax.imageio.ImageIO; import javax.swing.JComponent; import javax.swing.JFrame; import javax.swing.JLayeredPane; import javax.swing.JPanel; import javax.swing.UIManager; import javax.swing.UnsupportedLookAndFeelException; public class MapLayers { public static void main(String[] args) { new MapLayers(); } public MapLayers() { EventQueue.invokeLater(new Runnable() { @Override public void run() { try { UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) { } MapPane mapPane = new MapPane(); try { mapPane.addLayer(new ImageLayer(ImageIO.read(new File("Ponie.png")), 360, 10)); mapPane.addLayer(new ImageLayer(ImageIO.read(new File("Layer01.png")), 0, 0)); } catch (IOException ex) { ex.printStackTrace(); } JFrame frame = new JFrame("Testing"); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setLayout(new BorderLayout()); frame.add(mapPane); frame.pack(); frame.setLocationRelativeTo(null); frame.setVisible(true); } }); } public class ImageLayer extends JComponent { private Image bg; private int xOffset; private int yOffset; public ImageLayer(Image image, int x, int y) { bg = image; xOffset = x; yOffset = y; } @Override protected void paintComponent(Graphics g) { super.paintComponent(g); if (bg != null) { Graphics2D g2d = (Graphics2D) g.create(); g2d.drawImage(bg, xOffset, yOffset, this); g2d.dispose(); } } } public class MapPane extends JLayeredPane { private BufferedImage bg; public MapPane() { try { bg = ImageIO.read(new File("PirateMap.jpg")); } catch (IOException exp) { exp.printStackTrace(); } setLayout(new GridBagLayout()); } public void addLayer(JComponent layer) { GridBagConstraints gbc = new GridBagConstraints(); gbc.gridx = 0; gbc.gridy = 0; gbc.weightx = 1; gbc.weighty = 1; gbc.fill = GridBagConstraints.BOTH; add(layer, gbc); } @Override public Dimension getPreferredSize() { return bg == null ? new Dimension(200, 200) : new Dimension(bg.getWidth(), bg.getHeight()); } @Override protected void paintComponent(Graphics g) { super.paintComponent(g); if (bg != null) { Graphics2D g2d = (Graphics2D) g.create(); int x = (getWidth() - bg.getWidth()) / 2; int y = (getHeight()- bg.getHeight()) / 2; g2d.drawImage(bg, x, y, this); g2d.dispose(); } } } } 

See How to use LayeredPanes for more information.

+5
source

Do you intend to make transparent JPanel ? You can call setOpaque(false) , which will prevent flooding the background panel. The Swing tutorial section has some useful stack information.

+3
source

Source: https://habr.com/ru/post/1494419/


All Articles