Java Swing - 如何堆叠用户名文本字段和密码文本字段

Java Swing - How to stack Username textfield and Password textfield

我正在为我的布局使用 gridbaglayout,我想知道如何重新排列它,以便用户名文本字段直接位于密码文本字段上方,而登录按钮位于密码文本字段下方。

目前我的代码输出:

但是我想要这样的东西:

我的代码:

import javax.swing.*;
import java.awt.*;
import java.awt.event.*;

public class TestingJavaCode {

    public TestingJavaCode() {

        JFrame appFrame = new JFrame();
        JPanel loginPanel = new JPanel();
        appFrame.setSize(1200, 800);
        loginPanel = new JPanel(new GridBagLayout());


        // Button for logging in, with respective GridBagConstraint
        // setFocusable is set to false to take out the border around the text
        JButton loginButton = new JButton("Login");
        GridBagConstraints lButtonC = new GridBagConstraints();
        loginButton.setFocusable(false);


        // Username text-field and JLabel with respective GridBagConstraints
        JTextField tfUsername = new JTextField(15);
        GridBagConstraints tfUserC = new GridBagConstraints();
        JLabel txtUser = new JLabel("Username: ");
        GridBagConstraints txtUserC = new GridBagConstraints();


        // Password text-field and JLabel with respective GridBagConstraints
        JPasswordField tfPassword = new JPasswordField(15);
        GridBagConstraints tfPassC = new GridBagConstraints();
        JLabel txtPassword = new JLabel("Password: ");
        GridBagConstraints txtPassC = new GridBagConstraints();

        // Add all components to the JFrame
        // Making sure to add the text before the text-fields
        loginPanel.add(txtUser, txtUserC);
        loginPanel.add(tfUsername, tfUserC);
        loginPanel.add(txtPassword, txtPassC);
        loginPanel.add(tfPassword, tfPassC);
        loginPanel.add(loginButton, lButtonC);

        // Show the frame
        appFrame.add(loginPanel);
        appFrame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
        appFrame.setVisible(true);
    }


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

}

编辑:我愿意使用其他布局管理器。

既然您不想使用 gridx/y 约束,您为什么不使用 BoxLayout and FlowLayout 的组合?我添加了新的 2 个新面板。一个用于用户名,一个用于密码,并且由于 FlowLayout 是面板的默认布局,我们可以保持原样。

FlowLayout is the default layout manager for every JPanel. It simply lays out components in a single row, starting a new row if its container is not sufficiently wide.

之后让我们将 BoxLayout 设置为您的 loginPanel 并向其添加用户名和密码面板。

The BoxLayout class puts components in a single row or column. It respects the components' requested maximum sizes and also lets you align components.

这是完整的更新源:

import javax.swing.*;

public class TestingJavaCode {

    public TestingJavaCode() {

        JFrame appFrame = new JFrame();
        JPanel loginPanel = new JPanel();
        appFrame.setSize(300, 130);
        loginPanel.setLayout(new BoxLayout(loginPanel, BoxLayout.PAGE_AXIS));

        // Button for logging in, with respective GridBagConstraint
        // setFocusable is set to false to take out the border around the text
        JButton loginButton = new JButton("Login");
        loginButton.setFocusable(false);

        JPanel usernamePanel = new JPanel();
        // Username text-field and JLabel with respective GridBagConstraints
        JTextField tfUsername = new JTextField(15);
        JLabel txtUser = new JLabel("Username: ");

        usernamePanel.add(txtUser);
        usernamePanel.add(tfUsername);

        JPanel passwordPanel = new JPanel();
        // Password text-field and JLabel with respective GridBagConstraints
        JPasswordField tfPassword = new JPasswordField(15);
        JLabel txtPassword = new JLabel("Password: ");

        passwordPanel.add(txtPassword);
        passwordPanel.add(tfPassword);

        // Add all components to the JFrame
        // Making sure to add the text before the text-fields
        loginPanel.add(usernamePanel);

        loginPanel.add(usernamePanel);
        loginPanel.add(passwordPanel);
        loginPanel.add(loginButton);
        // Show the frame
        appFrame.add(loginPanel);
        appFrame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
        appFrame.setVisible(true);
    }

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

}