Java 设置BoxLayout后,此GUI不显示任何内容

Java 设置BoxLayout后,此GUI不显示任何内容,java,swing,user-interface,layout-manager,boxlayout,Java,Swing,User Interface,Layout Manager,Boxlayout,我尝试添加BoxLayout,因为所有文本字段和标签都在一行上。所以我尝试了框布局,但失败了 谁能告诉我如何使它像标题一样一行,标签不同的行,按钮不同的行 像这样: 正如camickr在评论中所说,您通常使用GridBagLayout来创建表单 我重新编写了您的代码,因为我希望展示一种更好的编写GUI面板代码的方法 这是GUI 我所做的主要改变包括: 所有Swing应用程序都必须以调用SwingUtilitiesinvokeLater方法开始。此方法确保在上创建并执行所有Swing组件 我将

我尝试添加
BoxLayout
,因为所有文本字段和标签都在一行上。所以我尝试了框布局,但失败了

谁能告诉我如何使它像标题一样一行,标签不同的行,按钮不同的行

像这样:


正如camickr在评论中所说,您通常使用
GridBagLayout
来创建表单

我重新编写了您的代码,因为我希望展示一种更好的编写GUI面板代码的方法

这是GUI

我所做的主要改变包括:

  • 所有Swing应用程序都必须以调用
    SwingUtilities
    invokeLater
    方法开始。此方法确保在上创建并执行所有Swing组件

  • 我将GUI代码组织为三种方法,以便一次只关注GUI的一部分。
    JFrame
    是在
    run
    方法中创建的。标题
    JPanel
    是在
    createTitlePanel
    方法中创建的。表单
    JPanel
    是在
    createFormPanel
    方法中创建的。
    JFrame
    的代码很少在Swing应用程序之间更改

  • 我使用Swing组件。我不扩展Swing组件或任何Java类,除非我打算重写其中一个类方法

  • createFormPanel
    类使用
    GridBagLayout
    来组织列中的标签和文本字段。您可以将
    GridBagLayout
    视为一个灵活的网格。网格单元的大小不必相同。Oracle教程还有一个例子

  • 我将
    ActionListener
    放在一个单独的类中。在本例中,我将其作为一个内部类,以便将代码粘贴为一个文件。通常,您应该将单独的类放在单独的文件中。它使每节课更短,更容易理解

  • 下面是可运行的示例代码

    import javax.swing.*;
    import java.awt.*;
    import java.awt.event.*;
    
    public class GUI_Borrower extends JFrame implements ActionListener {
    
        JPanel panel = new JPanel();
    
        JLabel lblName = new JLabel("Name:");
        JLabel lblProg = new JLabel("Program:");
        JLabel lblId = new JLabel("Library ID: ");
        JLabel lblTitle = new JLabel("Add Borrower");
        JTextField txtName = new JTextField(10);
        JTextField txtProg = new JTextField(10);
        JTextField txtId = new JTextField(10);
        static int counter = 19000;
        JButton btnSubmit = new JButton("Submit");
    
        public GUI_Borrower() {
            super("Add Borrower");
            makeFrame();
            showFrame();
        }
    
        public void makeFrame() {
            lblTitle.setFont(new Font("Forte", Font.PLAIN, 40));
            lblTitle.setForeground(Color.BLUE);
            add(lblTitle);
            add(lblName);
            add(txtName);
            add(lblProg);
            add(txtProg);
            add(lblId);
            add(txtId);
    
            panel.setLayout(new BoxLayout(panel, BoxLayout.PAGE_AXIS));
            panel.add(btnSubmit);
            btnSubmit.addActionListener(this);
        }
    
        public void showFrame() {
            setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            setSize(400, 200);
            setLocationRelativeTo(null);
            setVisible(true);
        }
    
        public void actionPerformed(ActionEvent ae) {
            Object source = ae.getSource();
    
            if (ae.getActionCommand().equals("Confirm")) {
                txtName.setText("");
                txtProg.setText("");
                btnSubmit.setText("Submit");
            } else if (source == btnSubmit) {
                if (txtName.getText().equals("") && txtProg.getText().equals("")) {
                    txtId.setText("No entry of both");
                } else if (txtName.getText().equals("")) {
                    txtId.setText("No entry of Name");
                } else if (txtProg.getText().equals("")) {
                    txtId.setText("No entry of Program");
                } else {
                    counter++;
                    txtId.setText("" + counter);
    
                    btnSubmit.setText("Confirm");
                }
            }
        }
    
        public static void main(String[] args) {
            new GUI_Borrower();
        }
    }
    
    编辑以添加:如果希望标题
    JLabel
    右对齐,则必须切换到
    BorderLayout
    。我添加了一个空边框,这样文本就不会位于
    JFrame
    的右边缘

    这是改变后的方法

    import java.awt.BorderLayout;
    import java.awt.Color;
    import java.awt.FlowLayout;
    import java.awt.Font;
    import java.awt.GridBagConstraints;
    import java.awt.GridBagLayout;
    import java.awt.Insets;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    
    import javax.swing.BorderFactory;
    import javax.swing.JButton;
    import javax.swing.JFrame;
    import javax.swing.JLabel;
    import javax.swing.JPanel;
    import javax.swing.JTextField;
    import javax.swing.SwingUtilities;
    
    public class BorrowerGUI implements Runnable {
    
        private static int ID_COUNTER = 19000;
    
        public static void main(String[] args) {
            SwingUtilities.invokeLater(new BorrowerGUI());
        }
    
        private JButton btnSubmit;
    
        private JTextField txtName;
        private JTextField txtProg;
        private JTextField txtId;
    
        @Override
        public void run() {
            JFrame frame = new JFrame("Add Borrower");
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    
            frame.add(createTitlePanel(), BorderLayout.BEFORE_FIRST_LINE);
            frame.add(createFormPanel(), BorderLayout.CENTER);
    
            frame.pack();
            frame.setLocationByPlatform(true);
            frame.setVisible(true);
        }
    
        private JPanel createTitlePanel() {
            JPanel panel = new JPanel(new FlowLayout());
    
            JLabel lblTitle = new JLabel("Add Borrower");
            lblTitle.setFont(new Font("Forte", Font.PLAIN, 40));
            lblTitle.setForeground(Color.BLUE);
            panel.add(lblTitle);
    
            return panel;
        }
    
        private JPanel createFormPanel() {
            JPanel panel = new JPanel(new GridBagLayout());
            panel.setBorder(BorderFactory.createEmptyBorder(5, 5, 5, 5));
    
            GridBagConstraints gbc = new GridBagConstraints();
            gbc.anchor = GridBagConstraints.LINE_START;
            gbc.fill = GridBagConstraints.HORIZONTAL;
            gbc.insets = new Insets(5, 5, 5, 5);
            gbc.gridx = 0;
            gbc.gridy = 0;
    
            JLabel lblName = new JLabel("Name:");
            panel.add(lblName, gbc);
    
            gbc.gridx++;
            txtName = new JTextField(20);
            panel.add(txtName, gbc);
    
            gbc.gridx = 0;
            gbc.gridy++;
            JLabel lblProg = new JLabel("Program:");
            panel.add(lblProg, gbc);
    
            gbc.gridx++;
            txtProg = new JTextField(20);
            panel.add(txtProg, gbc);
    
            gbc.gridx = 0;
            gbc.gridy++;
            JLabel lblId = new JLabel("Library ID:");
            panel.add(lblId, gbc);
    
            gbc.gridx++;
            txtId = new JTextField(20);
            txtId.setEditable(false);
            panel.add(txtId, gbc);
    
            gbc.gridx = 0;
            gbc.gridy++;
            gbc.gridwidth = 2;
            btnSubmit = new JButton("Submit");
            btnSubmit.addActionListener(new SubmitListener());
            panel.add(btnSubmit, gbc);
    
            return panel;
        }
    
        public class SubmitListener implements ActionListener {
    
            @Override
            public void actionPerformed(ActionEvent ae) {
                Object source = ae.getSource();
    
                if (ae.getActionCommand().equals("Confirm")) {
                    txtName.setText("");
                    txtName.requestFocus();
                    txtProg.setText("");
                    txtId.setText("");
                    btnSubmit.setText("Submit");
                } else if (source == btnSubmit) {
                    if (txtName.getText().equals("") &&
                            txtProg.getText().equals("")) {
                        txtId.setText("No entry of both");
                    } else if (txtName.getText().equals("")) {
                        txtId.setText("No entry of Name");
                    } else if (txtProg.getText().equals("")) {
                        txtId.setText("No entry of Program");
                    } else {
                        ID_COUNTER++;
                        txtId.setText("" + ID_COUNTER);
                        btnSubmit.setText("Confirm");
                    }
                }
    
            }
        }
    }
    

    正如camickr在评论中所说,通常使用
    GridBagLayout
    创建表单

    我重新编写了您的代码,因为我希望展示一种更好的编写GUI面板代码的方法

    这是GUI

    我所做的主要改变包括:

  • 所有Swing应用程序都必须以调用
    SwingUtilities
    invokeLater
    方法开始。此方法确保在上创建并执行所有Swing组件

  • 我将GUI代码组织为三种方法,以便一次只关注GUI的一部分。
    JFrame
    是在
    run
    方法中创建的。标题
    JPanel
    是在
    createTitlePanel
    方法中创建的。表单
    JPanel
    是在
    createFormPanel
    方法中创建的。
    JFrame
    的代码很少在Swing应用程序之间更改

  • 我使用Swing组件。我不扩展Swing组件或任何Java类,除非我打算重写其中一个类方法

  • createFormPanel
    类使用
    GridBagLayout
    来组织列中的标签和文本字段。您可以将
    GridBagLayout
    视为一个灵活的网格。网格单元的大小不必相同。Oracle教程还有一个例子

  • 我将
    ActionListener
    放在一个单独的类中。在本例中,我将其作为一个内部类,以便将代码粘贴为一个文件。通常,您应该将单独的类放在单独的文件中。它使每节课更短,更容易理解

  • 下面是可运行的示例代码

    import javax.swing.*;
    import java.awt.*;
    import java.awt.event.*;
    
    public class GUI_Borrower extends JFrame implements ActionListener {
    
        JPanel panel = new JPanel();
    
        JLabel lblName = new JLabel("Name:");
        JLabel lblProg = new JLabel("Program:");
        JLabel lblId = new JLabel("Library ID: ");
        JLabel lblTitle = new JLabel("Add Borrower");
        JTextField txtName = new JTextField(10);
        JTextField txtProg = new JTextField(10);
        JTextField txtId = new JTextField(10);
        static int counter = 19000;
        JButton btnSubmit = new JButton("Submit");
    
        public GUI_Borrower() {
            super("Add Borrower");
            makeFrame();
            showFrame();
        }
    
        public void makeFrame() {
            lblTitle.setFont(new Font("Forte", Font.PLAIN, 40));
            lblTitle.setForeground(Color.BLUE);
            add(lblTitle);
            add(lblName);
            add(txtName);
            add(lblProg);
            add(txtProg);
            add(lblId);
            add(txtId);
    
            panel.setLayout(new BoxLayout(panel, BoxLayout.PAGE_AXIS));
            panel.add(btnSubmit);
            btnSubmit.addActionListener(this);
        }
    
        public void showFrame() {
            setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            setSize(400, 200);
            setLocationRelativeTo(null);
            setVisible(true);
        }
    
        public void actionPerformed(ActionEvent ae) {
            Object source = ae.getSource();
    
            if (ae.getActionCommand().equals("Confirm")) {
                txtName.setText("");
                txtProg.setText("");
                btnSubmit.setText("Submit");
            } else if (source == btnSubmit) {
                if (txtName.getText().equals("") && txtProg.getText().equals("")) {
                    txtId.setText("No entry of both");
                } else if (txtName.getText().equals("")) {
                    txtId.setText("No entry of Name");
                } else if (txtProg.getText().equals("")) {
                    txtId.setText("No entry of Program");
                } else {
                    counter++;
                    txtId.setText("" + counter);
    
                    btnSubmit.setText("Confirm");
                }
            }
        }
    
        public static void main(String[] args) {
            new GUI_Borrower();
        }
    }
    
    编辑以添加:如果希望标题
    JLabel
    右对齐,则必须切换到
    BorderLayout
    。我添加了一个空边框,这样文本就不会位于
    JFrame
    的右边缘

    这是改变后的方法

    import java.awt.BorderLayout;
    import java.awt.Color;
    import java.awt.FlowLayout;
    import java.awt.Font;
    import java.awt.GridBagConstraints;
    import java.awt.GridBagLayout;
    import java.awt.Insets;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    
    import javax.swing.BorderFactory;
    import javax.swing.JButton;
    import javax.swing.JFrame;
    import javax.swing.JLabel;
    import javax.swing.JPanel;
    import javax.swing.JTextField;
    import javax.swing.SwingUtilities;
    
    public class BorrowerGUI implements Runnable {
    
        private static int ID_COUNTER = 19000;
    
        public static void main(String[] args) {
            SwingUtilities.invokeLater(new BorrowerGUI());
        }
    
        private JButton btnSubmit;
    
        private JTextField txtName;
        private JTextField txtProg;
        private JTextField txtId;
    
        @Override
        public void run() {
            JFrame frame = new JFrame("Add Borrower");
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    
            frame.add(createTitlePanel(), BorderLayout.BEFORE_FIRST_LINE);
            frame.add(createFormPanel(), BorderLayout.CENTER);
    
            frame.pack();
            frame.setLocationByPlatform(true);
            frame.setVisible(true);
        }
    
        private JPanel createTitlePanel() {
            JPanel panel = new JPanel(new FlowLayout());
    
            JLabel lblTitle = new JLabel("Add Borrower");
            lblTitle.setFont(new Font("Forte", Font.PLAIN, 40));
            lblTitle.setForeground(Color.BLUE);
            panel.add(lblTitle);
    
            return panel;
        }
    
        private JPanel createFormPanel() {
            JPanel panel = new JPanel(new GridBagLayout());
            panel.setBorder(BorderFactory.createEmptyBorder(5, 5, 5, 5));
    
            GridBagConstraints gbc = new GridBagConstraints();
            gbc.anchor = GridBagConstraints.LINE_START;
            gbc.fill = GridBagConstraints.HORIZONTAL;
            gbc.insets = new Insets(5, 5, 5, 5);
            gbc.gridx = 0;
            gbc.gridy = 0;
    
            JLabel lblName = new JLabel("Name:");
            panel.add(lblName, gbc);
    
            gbc.gridx++;
            txtName = new JTextField(20);
            panel.add(txtName, gbc);
    
            gbc.gridx = 0;
            gbc.gridy++;
            JLabel lblProg = new JLabel("Program:");
            panel.add(lblProg, gbc);
    
            gbc.gridx++;
            txtProg = new JTextField(20);
            panel.add(txtProg, gbc);
    
            gbc.gridx = 0;
            gbc.gridy++;
            JLabel lblId = new JLabel("Library ID:");
            panel.add(lblId, gbc);
    
            gbc.gridx++;
            txtId = new JTextField(20);
            txtId.setEditable(false);
            panel.add(txtId, gbc);
    
            gbc.gridx = 0;
            gbc.gridy++;
            gbc.gridwidth = 2;
            btnSubmit = new JButton("Submit");
            btnSubmit.addActionListener(new SubmitListener());
            panel.add(btnSubmit, gbc);
    
            return panel;
        }
    
        public class SubmitListener implements ActionListener {
    
            @Override
            public void actionPerformed(ActionEvent ae) {
                Object source = ae.getSource();
    
                if (ae.getActionCommand().equals("Confirm")) {
                    txtName.setText("");
                    txtName.requestFocus();
                    txtProg.setText("");
                    txtId.setText("");
                    btnSubmit.setText("Submit");
                } else if (source == btnSubmit) {
                    if (txtName.getText().equals("") &&
                            txtProg.getText().equals("")) {
                        txtId.setText("No entry of both");
                    } else if (txtName.getText().equals("")) {
                        txtId.setText("No entry of Name");
                    } else if (txtProg.getText().equals("")) {
                        txtId.setText("No entry of Program");
                    } else {
                        ID_COUNTER++;
                        txtId.setText("" + ID_COUNTER);
                        btnSubmit.setText("Confirm");
                    }
                }
    
            }
        }
    }
    

    在makeFrame()或showFrame()中,框架的默认布局管理器是
    边框布局
    。将组件添加到无约束的框架时,组件将转到
    BorderLayout.CENTER
    约束,该约束只能显示单个组件,因此只有最后添加的组件可见。阅读上的Swing教程中的部分。您可以下载工作演示,然后进行更改。我建议您可以使用
    GridBagLayout
    来实现所需的布局。在makeFrame()或showFrame()中,框架的默认布局管理器是
    BorderLayout
    。将组件添加到无约束的框架时,组件将转到
    BorderLayout.CENTER
    约束,该约束只能显示单个组件,因此只有最后添加的组件可见。阅读上的Swing教程中的部分。您可以下载工作演示,然后进行更改。我建议您可以使用
    GridBagLayout
    来实现所需的布局。非常感谢Gilbert,我会仔细阅读代码,询问我是否理解任何内容。我感谢你的帮助,因为你使我的工作更容易。如何在这个布局中进行allignment更改?比如(FlowLayout.RIGHT)?@Arvind Varma:哪种路线改变了?标题面板布局居中。您可以更改JPanel的背景颜色以查看其大小和方向。名称、程序、id向右对齐,如上图所示。非常感谢Gilbert,我将查看代码并询问我是否理解任何内容。我感谢你的帮助,因为你使我的工作更容易。如何在这个布局中进行allignment更改?比如(FlowLayout.RIGHT)?@Arvind Var