Java – layering multiple glasspanes in the root container
Can I add multiple glasspanes to a single JFrame, or do I have to use uncomfortable layeredpane and opacity attributes
I attached some code showing what I want to do (provided by @ camickr)
import java.awt.*; import java.awt.event.*; import java.util.*; import javax.swing.*; import javax.swing.border.*; public class MultiplayGlassPane { private static final long serialVersionUID = 1L; private JFrame frame = new JFrame("frameTitle"); private JPanel fPanel = new JPanel(); private Random random = new Random(); private final static Border MESSAGE_BORDER = new EmptyBorder(10,10,10); private JLabel message = new JLabel(); private ArrayList<Star> stars = new ArrayList<Star>(); public MultiplayGlassPane() { MyGlassPane glass = new MyGlassPane(); for (int i = 0; i < 35; i++) { Star star = new Star(new Point(random.nextInt(580),random.nextInt(550))); star.setColor(Color.orange); star.setxIncr(-3 + random.nextInt(7)); star.setyIncr(-3 + random.nextInt(7)); glass.add(star); } frame.setDefaultCloSEOperation(JFrame.EXIT_ON_CLOSE); frame.add(glass,BorderLayout.CENTER); frame.setLocation(20,20); frame.pack(); frame.setVisible(true); DisabledGlassPane1 glassPane = new DisabledGlassPane1(); JRootPane rootPane = SwingUtilities.getRootPane(frame); rootPane.setGlassPane(glassPane); glassPane.activate(""); } private class MyGlassPane extends JLabel { private static final long serialVersionUID = 1L; private ArrayList<Star> stars = new ArrayList<Star>(); private javax.swing.Timer timer = new javax.swing.Timer(20,new ActionListener() { @Override public void actionPerformed(ActionEvent e) { for (Star star : stars) { star.move(); } repaint(); } }); public void stopAnimation() { if (timer.isRunning()) { timer.stop(); } } public void startAnimation() { if (!timer.isRunning()) { timer.start(); } } @Override public void addNotify() { super.addNotify(); timer.start(); } @Override public void removeNotify() { super.removeNotify(); timer.stop(); } @Override public Dimension getPreferredSize() { return new Dimension(new Dimension(620,620)); } public MyGlassPane() { this.setPreferredSize(new Dimension(620,620)); } public void add(Star star) { stars.add(star); } @Override public void paintComponent(Graphics g) { super.paintComponent(g); ((Graphics2D) g).setRenderingHint(RenderingHints.KEY_ANTIALIASING,RenderingHints.VALUE_ANTIALIAS_ON); for (Star star : stars) { g.setColor(star.getColor()); g.fillPolygon(star); } } } class DisabledGlassPane1 extends JComponent implements KeyListener { private static final long serialVersionUID = 1L; public DisabledGlassPane1() { setOpaque(false); Color base = UIManager.getColor("inactiveCaptionBorder"); Color background = new Color(base.getRed(),base.getGreen(),base.getBlue(),128); setBackground(background); setLayout(new GridBagLayout()); add(message,new GridBagConstraints()); message.setOpaque(true); message.setBorder(MESSAGE_BORDER); addMouseListener(new MouseAdapter() { }); addMouseMotionListener(new MouseMotionAdapter() { }); addKeyListener(this); setFocusTraversalKeysEnabled(false); Random random = new Random(); for (int i = 0; i < 50; i++) { Star star = new Star(new Point(random.nextInt(490),random.nextInt(490))); star.setColor(Color.magenta); star.setxIncr(-3 + random.nextInt(7)); star.setyIncr(-3 + random.nextInt(7)); add(star); } } @Override protected void paintComponent(Graphics g) { super.paintComponent(g); ((Graphics2D) g).setRenderingHint(RenderingHints.KEY_ANTIALIASING,RenderingHints.VALUE_ANTIALIAS_ON); for (Star star : stars) { g.setColor(star.getColor()); g.fillPolygon(star); } } @Override public void setBackground(Color background) { super.setBackground(background); Color messageBackground = new Color(background.getRGB()); message.setBackground(messageBackground); } public void keyPressed(KeyEvent e) { e.consume(); } public void keyTyped(KeyEvent e) { } public void keyReleased(KeyEvent e) { e.consume(); } public void activate(String text) { if (text != null && text.length() > 0) { message.setVisible(true); message.setText(text); message.setForeground(getForeground()); } else { message.setVisible(false); } setVisible(true); //setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR)); requestFocusInWindow(); } public void deactivate() { setCursor(null); setVisible(false); } private javax.swing.Timer timer = new javax.swing.Timer(15,new ActionListener() { @Override public void actionPerformed(ActionEvent e) { for (Star star : stars) { star.move(); } repaint(); } }); public void stopAnimation() { if (timer.isRunning()) { timer.stop(); } } public void startAnimation() { if (!timer.isRunning()) { timer.start(); } } @Override public void addNotify() { super.addNotify(); timer.start(); } @Override public void removeNotify() { super.removeNotify(); timer.stop(); } public void add(Star star) { stars.add(star); } } private class Star extends Polygon { private static final long serialVersionUID = 1L; private Point location = null; private Color color = Color.YELLOW; private int xIncr,yIncr; static final int WIDTH = 600,HEIGHT = 600; Star(Point location) { int x = location.x; int y = location.y; this.location = location; this.addPoint(x,y + 8); this.addPoint(x + 8,y + 8); this.addPoint(x + 11,y); this.addPoint(x + 14,y + 8); this.addPoint(x + 22,y + 8); this.addPoint(x + 17,y + 12); this.addPoint(x + 21,y + 20); this.addPoint(x + 11,y + 14); this.addPoint(x + 3,y + 20); this.addPoint(x + 6,y + 12); } public void setColor(Color color) { this.color = color; } public void move() { if (location.x < 0 || location.x > frame.getContentPane().getWidth() - 20) { xIncr = -xIncr; } if (location.y < 0 || location.y > frame.getContentPane().getHeight() - 20) { yIncr = -yIncr; } translate(xIncr,yIncr); location.setLocation(location.x + xIncr,location.y + yIncr); } public void setxIncr(int xIncr) { this.xIncr = xIncr; } public void setyIncr(int yIncr) { this.yIncr = yIncr; } public Color getColor() { return color; } } public static void main(String[] args) { SwingUtilities.invokelater(new Runnable() { @Override public void run() { MultiplayGlassPane Mpgp = new MultiplayGlassPane(); } }); } }
Solution
see http://docs.oracle.com/javase/tutorial/uiswing/components/rootpane.html For a description of the root pane and what the glass pane is actually
The glass pane is just a convenient way to add components with the size of the root pane. It can block all input events This allows you to capture any interaction with the component to create a "please wait..." screen
Each root container has only one glass pane You can't layer glass panes
If you want to stack on the current pane, you can replace the contents of the pane with something else You can also set JPanel as a glass pane, which allows you to layout multiple components in the glass pane
In general, you should only use glass panes to block user input (and display some "please wait" message if necessary) Can you provide a use case to explain why the glass panes are put together?