为什么 setBackground 只在第一次起作用? (J面板)

Why setBackground works only the first time? (JPanel)

在外部 class 我多次调用这些方法,但 setBackground() 仅在我第一次调用这些方法时起作用。

例如,我有对象 CellPane cellpane1, cellpane2,当我第一次调用 cellpane1.drawPlayer() 时,它按预期工作,而当我第一次调用 cellpane2.drawWall() 时,它按预期工作也。但是当我为 cellpane1 调用 drawWall() 时,在我调用 cellpane1.drawPlayer() 之后 cellpane1.drawWall(),它不起作用。背景颜色没有变化。

我需要重新粉刷或重新生效,还是什么?我对这些东西很陌生。 :( 我做错了什么?

private static class CellPane extends JPanel {

    private Color defaultBackground;

    private CellPane() {
        addMouseListener(new MouseAdapter() {
            @Override
            public void mouseEntered(MouseEvent e) {
                defaultBackground = getBackground();
                setBackground(Color.BLUE);
            }

            @Override
            public void mouseExited(MouseEvent e) {
                setBackground(defaultBackground);
            }
        });
    }

    private void drawDefault() {
        setBackground(defaultBackground);
    }

    private void drawBoxOnGoal() {
        defaultBackground = getBackground();
        setBackground(Color.decode("#4a3d32"));
    }

    private void drawPlayerOnGoal() {
        defaultBackground = getBackground();
        setBackground(Color.decode("#f9cda8"));
    }

    private void drawGoal() {
        defaultBackground = getBackground();
        setBackground(Color.decode("#f9cda8"));
    }

    private void drawBox() {
        defaultBackground = getBackground();
        setBackground(Color.decode("#7a5230"));
    }

    private void drawPlayer() {
        defaultBackground = getBackground();
        setBackground(Color.YELLOW);

    }

    private void drawWall() {
        defaultBackground = getBackground();
        setBackground(Color.RED);
    }

    @Override
    public Dimension getPreferredSize() {
        return new Dimension(50, 50);
    }

}

[编辑]

示例:

public class MainClass {



public static void main(String[] args) {
    new MainClass();
}

private MainClass() {
    EventQueue.invokeLater(new Runnable() {
        @Override
        public void run() {
            try {
                UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
            } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) { }

            JFrame frame = new JFrame("Test");
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.setLayout(new BorderLayout());

            frame.add(new Map());

            frame.pack();
            frame.setLocationRelativeTo(null);
            frame.setVisible(true);
        }
    });
}

private static class Map  extends JPanel implements ActionListener{

    CellPane cellPane;
    boolean flag = true;

    JButton button = new JButton("button");

    public Map() {
        setLayout(new GridBagLayout());

        button.addActionListener(this);

        add(button);

        create(flag);
    }

    public void create(boolean flag) {
        GridBagConstraints gbc = new GridBagConstraints();

        cellPane = new CellPane();
        gbc.gridx = 0;
        gbc.gridy = 0;
        if(flag)
            cellPane.drawPlayer();
        else cellPane.drawWall();
        add(cellPane, gbc);
    }

    @Override
    public void actionPerformed(ActionEvent arg0) {
        flag = false;
        create(flag);
    }

}


@SuppressWarnings("serial")
private static class CellPane extends JPanel {

    private Color defaultBackground;


    private void drawPlayer() {
        defaultBackground = getBackground();
        setBackground(Color.YELLOW);

    }

    private void drawWall() {
        defaultBackground = getBackground();
        setBackground(Color.RED);
    }

    @Override
    public Dimension getPreferredSize() {
        return new Dimension(50, 50);
    }

}}

我知道这不是完美的例子,但它是可以运行的。所以我想在单击按钮时更改 cellPane 的背景。当标志为真且背景设置为黄色时,构造函数调用 create(flag)。然后我单击按钮,标志更改为 false 并调用 create(flag) where flag=false,因此它调用 cellPane.setWall() 而不是将背景设置为红色,但它没有。

我做错了什么?也许很简单,但我是新手。

单击按钮时您没有更改 cellPane 的颜色。您正在创建另一个颜色不同的 cellPane,并将其添加到与现有单元格相同的 gridbag 单元格中。

只需更改颜色,即可正常使用:

    public Map() {
        setLayout(new GridBagLayout());

        button.addActionListener(this);

        add(button);

        create();
        draw();
    }

    private void draw() {
        if (flag) {
            cellPane.drawPlayer();
        }
        else {
            cellPane.drawWall();
        }
    }

    private void create() {
        GridBagConstraints gbc = new GridBagConstraints();

        cellPane = new CellPane();
        gbc.gridx = 0;
        gbc.gridy = 0;
        add(cellPane, gbc);
    }

    @Override
    public void actionPerformed(ActionEvent arg0) {
        flag = false;
        draw();
    }