2

我正在尝试重叠JPanel实例。将面板直接放在另一个面板上,位置和尺寸完全相同。每次我这样做时,它都会将另一个面板移动到另一侧或下方,前一个面板在另一个更大的面板内,并且里面有按钮。

我该怎么做?请记住,它使用的是 Window Builder 工具。

4

3 回答 3

9

你可能还想看看,在这里OverlayLayout见过。它不包含在传统画廊中,但可能会引起人们的兴趣。

叠加样本

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.OverlayLayout;

/** @see http://stackoverflow.com/a/13437388/230513 */
public class OverlaySample {

    public static void main(String args[]) {
        JFrame frame = new JFrame("Overlay Sample");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        JPanel panel = new JPanel();
        panel.setLayout(new OverlayLayout(panel));
        panel.add(create(1, "One", Color.gray.brighter()));
        panel.add(create(2, "Two", Color.gray));
        panel.add(create(3, "Three", Color.gray.darker()));
        frame.add(panel, BorderLayout.CENTER);
        frame.pack();
        frame.setLocationByPlatform(true);
        frame.setVisible(true);
    }

    private static JLabel create(final int index, String name, Color color) {
        JLabel label = new JLabel(name) {
            private static final int N = 64;

            @Override
            public boolean isOpaque() {
                return true;
            }

            @Override
            public Dimension getPreferredSize() {
                return new Dimension(index * N, index * N);
            }

            @Override
            public Dimension getMaximumSize() {
                return new Dimension(index * N, index * N);
            }
        };
        label.setHorizontalAlignment(JLabel.RIGHT);
        label.setVerticalAlignment(JLabel.BOTTOM);
        label.setBackground(color);
        label.setAlignmentX(0.0f);
        label.setAlignmentY(0.0f);
        return label;
    }
}
于 2012-11-18T04:08:15.070 回答
5

I'm attempting to overlap JPanels

Use a JLayeredPane (image below from the linked tutorial).

JLayeredPane

Put a JPanel directly on another,

..or a CardLayout as shown here..

..depending on which of those two you mean, since I understand them as quite different effects.

于 2012-11-18T02:09:32.277 回答
4

使用 a JDesktopPane(或其超类JLayeredPane)作为其内容,添加到窗格中。

有关示例,请参见如何使用内部框架

内部框架演示


在这里,您可以看到一种让组件叠加并在光标停留在其上时弹出的好方法:

import javax.swing.*;

import java.awt.*;
import java.awt.event.*;

public class ShiftedStackPanel extends JPanel implements MouseListener,
                                                            ActionListener {

    private static final long serialVersionUID = 1988454751139668485L;

    private int layer;
    private JDesktopPane desktopPane;
    private Timer timer;
    private Component currentComponent;
    private int layerOfCurrent;
    private int shiftDivision;

    public ShiftedStackPanel() {
        this(4);
    }

    public ShiftedStackPanel(int shift) {
        shiftDivision = shift;

        setLayout(new BorderLayout(0, 0));

        desktopPane = new JDesktopPane();
        desktopPane.setBackground(SystemColor.window);
        super.add(desktopPane);
        timer = new Timer(1000, this);
        timer.setRepeats(false);

    }

    public Component add(Component c) {
        Dimension dim = c.getPreferredSize();
        c.setBounds(
                (desktopPane.getComponentCount() * (dim.width / shiftDivision)),
                0, dim.width, dim.height);
        desktopPane.add(c, new Integer(++layer));
        c.addMouseListener(this);
        return c;
    }

    public void remove(Component c) {
        throw new IllegalArgumentException(
                "Removal of component, not yet supported.");
        // FIXME: allow removal, and shift all latter comps, to left
    }

    public void removeAll() {
        desktopPane.removeAll();
    }

    public static void main(String[] args) {
        JFrame f = new JFrame("JFrame Wrapper");
        ShiftedStackPanel p;
        f.setContentPane(p = new ShiftedStackPanel(4));
        p.add(new JTextField("ABCDEFGHI"));
        p.add(new JTextField("DEFGHIJKL"));
        p.add(new JTextField("GHIJKLMNO"));
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.setVisible(true);
        f.setMinimumSize(new Dimension(400, 200));
        f.setLocationRelativeTo(null);
    }

    @Override
    public void mouseClicked(MouseEvent evt) {
        if (currentComponent != null) {
            Component c = (Component) evt.getSource();
            currentComponent = c;
            layerOfCurrent = desktopPane.getLayer(c);
            desktopPane.remove(c);
            desktopPane.add(c, new Integer(100));
        }
    }

    @Override
    public void mouseEntered(MouseEvent evt) {
        timer.start();
        Component c = (Component) evt.getSource();
        currentComponent = c;
        layerOfCurrent = desktopPane.getLayer(c);
    }

    @Override
    public void mouseExited(MouseEvent evt) {
        if ((currentComponent != null) && currentComponent == evt.getSource()) {
            desktopPane.remove(currentComponent);
            desktopPane.add(currentComponent, new Integer(layerOfCurrent));
            currentComponent = null;
            timer.stop();
        }
    }

    @Override
    public void mousePressed(MouseEvent arg0) {
        // TODO Auto-generated method stub

    }

    @Override
    public void mouseReleased(MouseEvent arg0) {
        // TODO Auto-generated method stub

    }

    @Override
    public void actionPerformed(ActionEvent arg0) {

        desktopPane.remove(currentComponent);
        desktopPane.add(currentComponent, new Integer(100));
    }
}

在使用需要焦点的组件时仍然存在一些问题,但应该可以很好地与JLabel, 和JPanel.

于 2012-11-18T02:09:07.087 回答