Как cменить JPanel на лету?

398
10 октября 2017, 02:26

Делаю простенькую игру на Java. Представление следующее: Имеется JFrame mainFrame;, на нём JPanel menuPanel;, на котором JButton btnToGame;. Хочется, что бы при нажатии на кнопку menuPanel исчезала, но не разрушалась, а вместо неё появлялась JPanel gamePanel; уже со своим содержимым, но на ней тоже должна быть кнопка, допустим JButton btnToMenu;, которая опять возвращает нас в меню. Пытался писать так, но при нажатии на кнопку уже нарисованное виснет, а новое не появляется. Хотя если растянуть окно, то содержимое обновляется, но моё окно должно быть нерастяжимым.

public class MainFrame {
    private JFrame mainFrame;
    private JPanel menuPanel;
    private JPanel gamePanel;
    public static void main(String[] args){
        MainFrame frame = new MainFrame();
        frame.go();
    }
    public MainFrame() {
        mainFrame = new JFrame("Game Title"));
        mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        mainFrame.setSize(800, 600);
        mainFrame.setLocationRelativeTo(null);
        mainFrame.setResizable(false);
        menuPanel = new JPanel();
        menuPanel.setBackground(Color.ORANGE);
        menuPanel.setBorder(new EmptyBorder(5, 5, 5, 5));
        gamePanel = new JPanel();
        gamePanel.setBackground(Color.BLUE);
        gamePanel.setBorder(new EmptyBorder(5, 5, 5, 5));
        mainFrame.add(menuPanel);
        mainFrame.setUndecorated(true);
    }
    public void go() {
        JButton btnToGame = new JButton("To Game");
        JButton btnToMenu = new JButton("To Menu");
        btnToGame.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                mainFrame.removeAll();
                mainFrame.add(gamePanel);
            }
        });
        btnToMenu.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                mainFrame.removeAll();
                mainFrame.add(menuPanel);
            }
        });
        menuPanel.add(btnToGame);
        gamePanel.add(btnToMenu);
        mainFrame.setVisible(true);
    }
}
Answer 1

Используйте функцию JFrame.pack(), она позволяет "пересобрать" содержимое всего фрейма. И вместо removeAll() стоит использовать remove(Component comp). Возвращаю рабочий код:

public class MainFrame {
private JFrame mainFrame;
private JPanel menuPanel;
private JPanel gamePanel;
public static void main(String[] args){
    MainFrame frame = new MainFrame();
    frame.go();
}
public MainFrame() {
    mainFrame = new JFrame("Game Title");
    mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    mainFrame.setSize(800, 600);
    mainFrame.setLocationRelativeTo(null);
    mainFrame.setResizable(false);
    menuPanel = new JPanel();
    menuPanel.setBackground(Color.ORANGE);
    menuPanel.setBorder(new EmptyBorder(5, 5, 5, 5));
    gamePanel = new JPanel();
    gamePanel.setBackground(Color.BLUE);
    gamePanel.setBorder(new EmptyBorder(5, 5, 5, 5));
    mainFrame.add(menuPanel);
    mainFrame.setUndecorated(true);

}
public void go() {
    JButton btnToGame = new JButton("To Game");
    JButton btnToMenu = new JButton("To Menu");
    btnToGame.addActionListener((ActionEvent e) -> {
        mainFrame.remove(menuPanel);
        mainFrame.add(gamePanel);
        mainFrame.pack();
    });
    btnToMenu.addActionListener((ActionEvent e) -> {
        mainFrame.remove(gamePanel);
        mainFrame.add(menuPanel);
        mainFrame.pack();
    });
    menuPanel.add(btnToGame);
    gamePanel.add(btnToMenu);
    mainFrame.setVisible(true);
    }
}
READ ALSO
Ошибки в JFormDesigner плагине

Ошибки в JFormDesigner плагине

Установил в Inteliji Idea плагин jFormDesigner и при запуске созданной формы высвечивает ошибки:

213
Без AppCompatActivity метод отказывается работать

Без AppCompatActivity метод отказывается работать

Я хочу использовать диалоговое окно в текущем activity, но дело в том,что данный класс уже имеет наследника YouTubeBaseActivity, из-за этого отказывается...

252
Как создать глобальный массив?

Как создать глобальный массив?

Мне надо закинуть строки в массив, который был создан в классе

478