当前位置: 首页 > 知识库问答 >
问题:

Java摆动时刷新网格布局的问题

庄元龙
2023-03-14

我在刷新gridlayout的值时遇到问题。

因此,我在JFrame中有一个JPanel,在这个JPanel中,一旦我输入了两个值(一个用于行,一个用于列),然后单击validate,我就得到了一个包含JButtons之前值的GridLayout。例如,如果我输入(2,2),我会得到一个包含4个按钮的GridLayout,每个按钮中都有一个图像。

所以我的问题是,每次我想通过改变值来刷新GridLayout,它都不起作用,GridLayout不会改变,或者如果它改变了,JButton是可选择的。我觉得每次我点击验证,一个新的GridLayout就会在我的JPanel上创建,但是第一个仍然存在。

我将上传两张图片,一张具有正常功能(第一次输入值),第二张具有错误(输入新值)。

谢谢大家。

第一个值第二个值

import java.awt.Font;
import java.awt.GridLayout;
import java.awt.Color;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import java.awt.event.ActionEvent;
import javax.swing.*;




    public class PagePrincipal extends JFrame implements ActionListener {

    JButton Valider;
    JTextField Columns;
    JTextField Rows;
    ArrayList<JButton> butt;
   
    
    public PagePrincipal(){
        
        getContentPane().setLayout(null); //this is not the panel that contains the GridLayout
    
        Columns = new JTextField();
        Columns.setBounds(219, 35, 197, 57);
        getContentPane().add(Columns);
        Columns.setColumns(10);
        
        Rows = new JTextField();
        Rows.setBounds(451, 35, 226, 57);
        getContentPane().add(Rows);
        Rows.setColumns(10);
        
        Valider = new JButton();
        Valider.setBackground(new Color(65, 179, 163));
        Valider.setForeground(Color.WHITE);
        Valider.setFont(new Font("Bookman Old Style", Font.BOLD, 20));
        Valider.setBounds(704, 15, 268, 81);
        Valider.setText("Validation");
        Valider.addActionListener(this);
        this.add(Valider);

        
        this.setResizable(true);
        this.setVisible(true);
        this.setExtendedState(JFrame.MAXIMIZED_BOTH); 
        
        
        
        
        
    }
    

    @Override    
   
    
        
    public void actionPerformed(ActionEvent event) {

     if (event.getSource() == Valider) {   
        int NbRows= Integer.parseInt(Rows.getText());
        int NbColumns=Integer.parseInt(Columns.getText());
        JButton button[] = new JButton[NbRows*NbColumns];
        butt = new ArrayList<>();
       
        setDefaultCloseOperation(EXIT_ON_CLOSE);

        JPanel botPanel = new JPanel(); //this is the panel that contains the GridLayout
        botPanel.setBounds(100, 200, 1000, 400);
        this.add(botPanel);
        
        botPanel.setLayout(new GridLayout(NbRows,NbColumns));
        
        for (int i=0; i<NbRows*NbColumns; i++){
                button[i]=new JButton();
                botPanel.add(button[i]);
                butt.add(button[i]);    
        }
        this.setVisible(true);
        
    }
     
        
}
}

共有1个答案

龚远
2023-03-14

同样,尽可能避免空布局,因为它们迫使您创建可能只在一个平台上工作的僵硬、不灵活、难以维护的GUI。相反,nest JPanel是灵活的、可扩展的,并且可以正常工作,每个nest JPanel都使用自己的布局来帮助创建外观良好的GUI。

此外,当更改容器中的组件时,在进行更改后,在容器上调用revalidate()repaint()。例如,以下GUI:

使用以下代码创建:

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.GridLayout;
import java.util.ArrayList;
import java.util.List;

import javax.swing.*;

public class PagePrincipal2 extends JPanel {
    public static final int MAX_ROWS = 40;
    public static final int MAX_COLS = 12;
    private JButton validatorButton = new JButton("Validate");
    private JSpinner columnsSpinner = new JSpinner(new SpinnerNumberModel(2, 1, MAX_COLS, 1));
    private JSpinner rowsSpinner = new JSpinner(new SpinnerNumberModel(2, 1, MAX_ROWS, 1));
    private List<JButton> buttonsList = new ArrayList<>();
    private JPanel gridPanel = new JPanel();
    
    public PagePrincipal2() {
        JPanel topPanel = new JPanel();
        topPanel.add(new JLabel("Columns:"));
        topPanel.add(columnsSpinner);
        topPanel.add(Box.createHorizontalStrut(10));
        topPanel.add(new JLabel("Rows:"));
        topPanel.add(rowsSpinner);
        topPanel.add(Box.createHorizontalStrut(10));
        topPanel.add(validatorButton);
        
        JScrollPane scrollPane = new JScrollPane(gridPanel);
        
        int gridWidth = 1000;
        int gridHeight = 600;
        scrollPane.setPreferredSize(new Dimension(gridWidth, gridHeight));
        
        setLayout(new BorderLayout());
        add(topPanel, BorderLayout.PAGE_START);
        add(scrollPane, BorderLayout.CENTER);
        
        validatorButton.addActionListener(e -> validateGrid());
    }
    
    private void validateGrid() {
        int nbRows = (int) rowsSpinner.getValue();
        int nbColumns = (int) columnsSpinner.getValue();
        gridPanel.removeAll();
        buttonsList.clear();
        gridPanel.setLayout(new GridLayout(nbRows, nbColumns));
        for (int i = 0; i < nbRows * nbColumns; i++) {
            int column = i % nbColumns;
            int row = i / nbColumns;
            String text = String.format("[%02d, %02d]", column, row);
            JButton button = new JButton(text);
            button.addActionListener(e -> gridButtonAction(column, row));
            buttonsList.add(button);
            gridPanel.add(button);
        }
        gridPanel.revalidate();
        gridPanel.repaint();
    }
    
    private void gridButtonAction(int column, int row) {
        String message = String.format("Button pressed: [%02d, %02d]", column, row);
        String title = "Grid Button Press";
        int type = JOptionPane.INFORMATION_MESSAGE;
        JOptionPane.showMessageDialog(this, message, title, type);
    }
    
    public static void main(String[] args) {
        SwingUtilities.invokeLater(() -> {
            PagePrincipal2 mainPanel = new PagePrincipal2();

            JFrame frame = new JFrame("GUI");
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.add(mainPanel);
            frame.pack();
            frame.setLocationRelativeTo(null);
            frame.setVisible(true);
        });
    }
}

请注意,握着按钮的gridPanel被放置在JScrollPane中:

JScrollPane scrollPane = new JScrollPane(gridPanel);

请注意,保存所有内容的主JPanel被赋予了一个BorderLayout,然后添加了两个组件,一个topPanel JPanel,保存标签、按钮和数据输入字段,添加到BorderLayout。页面_START、顶部位置和JScrollPane被添加到边框布局的主JPanel中。居中位置:

setLayout(new BorderLayout());
add(topPanel, BorderLayout.PAGE_START);
add(scrollPane, BorderLayout.CENTER);

当旧按钮从gridPanel中删除,然后添加新按钮时,我将在gridPanel上调用重新验证()repaint(),第一个方法让布局管理器布局新组件,第二个方法调用以删除可能存在的任何脏像素:

private void validateGrid() {
    int nbRows = (int) rowsSpinner.getValue();
    int nbColumns = (int) columnsSpinner.getValue();
    gridPanel.removeAll();
    buttonsList.clear();
    gridPanel.setLayout(new GridLayout(nbRows, nbColumns));
    for (int i = 0; i < nbRows * nbColumns; i++) {
        int column = i % nbColumns;
        int row = i / nbColumns;
        String text = String.format("[%02d, %02d]", column, row);
        JButton button = new JButton(text);
        button.addActionListener(e -> gridButtonAction(column, row));
        buttonsList.add(button);
        gridPanel.add(button);
    }
    gridPanel.revalidate();
    gridPanel.repaint();
}
 类似资料:
  • 我正在学习如何使用Java Swing中的GridBagLayout。。。 在这个例子中,我想在每一行中放置4个元素,正如您在我的代码中看到的那样: 正如您在代码中看到的那样。 在第0行中,我想放置一个JLabel 在第1行中,我想放一个带有图标的JLabel 在第2行中,我想放置一个JTextField 在第3行中,我想在右侧放置一个JTextfield和JTextfield 最后在第4行,我想

  • 在我的摆动应用程序中,我在一个框架中有两个面板。第一个面板有一个按钮。当我单击此按钮时,一些数据会发生变化,我希望第二个面板的内容也会发生变化,显示新数据(通过jtag)。repaint()不起作用。我尝试了各种更新(参见代码中的注释)。 我提到了第二个小组。我可以使用该引用更改第二个面板的颜色,但无法重新绘制。我也可以在第二个面板中引用jlabel,只需更改其文本,但这个问题的重点是使panel

  • 我有一个Jtable,现在我想在这个Jtable上方的一行中有一个JLabel和一个JTextField和一个JButton。 我该怎么做? 直到现在我有了这个: 现在,我在上面添加了以下内容: 但是怎么做呢,这里有一个:“Filter:TEXTFIELD BUTTON”,下面是表格?

  • 我有种感觉,我不知道swing Timer是如何工作的。我对JavaGUI API还是新手,我编写的程序只是为了测试自己,帮助我更熟悉它的内部工作。 它应该做的是等待用户按下开始按钮,然后迭代显示(白色或黑色JPanel网格),以1秒的间隔显示一个简单的细胞自动机模拟,并在按下暂停按钮时暂停(与开始按钮相同,但更改名称)。网格中的每个单元格都应该以随机颜色(白色/黑色)开始。它所做的是暂停半秒左右

  • 我觉得摇摆计时器有问题。我写了一些运行良好的代码,然后将其全部移动到我的新计算机上,但它很快就无法工作。我用这个方法编写了一个GUI类(基于JFrame): 该方法是从另一个类调用的。真是太夸张了。splash guy是一个只运行splash动画的JPanel类。它通过摆动计时器来实现。在splash类中,侦听器通过以下代码调整我的帧的内容: 现在,如果第一个块中的print语句被注释掉,我的程序

  • 主要内容:本节引言,1.相关属性总结图,2.使用实例:计算器布局的实现:,3.用法归纳:,4.使用GridLayout要注意的地方:,5.低版本sdk如何使用GridLayout:,本节小结本节引言 今天要介绍的布局是Android 4.0以后引入的一个新的布局,和前面所学的TableLayout(表格布局) 有点类似,不过他有很多前者没有的东西,也更加好用, 可以自己设置布局中组件的排列方式 可以自定义网格布局有多少行,多少列 可以直接设置组件位于某行某列 可以设置组件横跨几行或者几列 另外,