Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/400.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
javagui打开一个新的JFrame_Java_Swing_User Interface_Jframe_Jbutton - Fatal编程技术网

javagui打开一个新的JFrame

javagui打开一个新的JFrame,java,swing,user-interface,jframe,jbutton,Java,Swing,User Interface,Jframe,Jbutton,我在网上查看了如何从现有JFrame打开新的JFrame。我发现,显然最好的方法是处理现有的JFrame并打开新的JFrame——然而这是一个问题 我有一个登录表单,一个用户登录的表单,登录框架被释放,主框架被设置为可见 import javax.swing.JFrame; import javax.swing.JButton; import java.awt.event.ActionListener; import java.awt.event.ActionEvent; public cla

我在网上查看了如何从现有JFrame打开新的JFrame。我发现,显然最好的方法是处理现有的JFrame并打开新的JFrame——然而这是一个问题

我有一个登录表单,一个用户登录的表单,登录框架被释放,主框架被设置为可见

import javax.swing.JFrame;
import javax.swing.JButton;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;

public class client {

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

    private static void initialize() {
        JFrame loginFrame = new JFrame("Login");
        loginFrame.setBounds(100, 100, 300, 300);
        loginFrame.setResizable(false);
        loginFrame.setLocationRelativeTo(null);
        loginFrame.setDefaultCloseOperation(loginFrame.HIDE_ON_CLOSE);
        loginFrame.getContentPane().setLayout(null);
        JFrame mainFrame = new JFrame("Main");
        mainFrame.setBounds(100, 100, 300, 197);
        mainFrame.setResizable(false);
        mainFrame.setLocationRelativeTo(null);
        mainFrame.setDefaultCloseOperation(mainFrame.EXIT_ON_CLOSE);
        mainFrame.getContentPane().setLayout(null);
        JButton loginButton = new JButton("Login");
        loginButton.setBounds(102, 133, 89, 23);
        loginButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                loginButton.setEnabled(false);
                loginFrame.dispose();
                mainFrame.setVisible(true);
            }
        });
        loginFrame.getContentPane().add(loginButton);
        loginFrame.setVisible(true);
    }
}
但是,如果用户启动客户端,然后决定不登录并关闭它,该进程是否仍在后台运行

我觉得这是一个非常愚蠢的问题,如果是这样的话,我很抱歉,但我环顾四周,找不到任何解决办法。我是否可以不处理登录框而将其隐藏并将其设置为在关闭时退出


提前谢谢

因此,主要问题是,您有两个帧,虽然不可见,但都已“实现”,这意味着在处理所有应用程序窗口之前,事件调度线程不会退出,这意味着JVM不会退出

因此,我建议在方法上稍作改变。而不是以这种方式使用两个框架,登录“窗口”应该基于一个模式对话框,应用程序框架应该在您需要它之前创建

模式拨号将在代码在不阻止事件调度线程的情况下(这是一个黑魔法)显示时停止代码的执行,这意味着您可以使用它作为一个循环来不断提示用户输入凭据,直到他们通过身份验证或关闭/取消对话框

我还强烈鼓励使用
JPanel
s作为基本组件,允许基于窗口的类只是容器,这将隔离责任,分离代码,并使整体解决方案更加可重用

您可以查看更多详细信息

import java.awt.EventQueue;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JPasswordField;
import javax.swing.JTextField;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.border.EmptyBorder;

public class Test {

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

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

                LoginPane loginPane = new LoginPane();
                boolean authenticated = false;
                boolean exit = false;
                do {
                    int option = JOptionPane.showOptionDialog(null,
                                    loginPane,
                                    "login",
                                    JOptionPane.OK_CANCEL_OPTION,
                                    JOptionPane.PLAIN_MESSAGE,
                                    null,
                                    new Object[]{"Login", "Cancel"},
                                    "Login");
                    if (option == 0) {
                        // Authenticate
                        authenticated = true;
                    } else if (option == JOptionPane.CLOSED_OPTION || option == 1) {
                        exit = true;
                    }
                } while (!authenticated && !exit);
                if (authenticated) {
                    JFrame frame = new JFrame();
                    frame.add(new MainPane());
                    frame.pack();
                    frame.setLocationRelativeTo(null);
                    frame.setVisible(true);
                }
            }
        });
    }

    public class LoginPane extends JPanel {

        private JTextField userName;
        private JPasswordField password;

        public LoginPane() {
            setLayout(new GridBagLayout());
            GridBagConstraints gbc = new GridBagConstraints();
            gbc.gridx = 0;
            gbc.gridy = 0;

            add(new JLabel("User name: "), gbc);
            gbc.gridy++;
            add(new JLabel("Password: "), gbc);

            gbc.gridx++;
            gbc.gridy = 0;

            userName = new JTextField(10);
            password = new JPasswordField(10);

            add(userName, gbc);
            gbc.gridy++;
            add(password, gbc);
        }

        public String getName() {
            return userName.getText();
        }

        public char[] getPassword() {
            return password.getPassword();
        }

    }

    public class MainPane extends JPanel {

        public MainPane() {
            setBorder(new EmptyBorder(50, 50, 50, 50));
            add(new JLabel("Super awesome app"));
        }

    }

}
我还鼓励
DISPOSE\u ON\u CLOSE
而不是
HIDE\u ON\u CLOSE
,它将释放本机对等机并从应用程序窗口缓存中删除窗口


现在,如果你真的想要一种更具挑战性的方法,你可以看看,它提供了一个基于MVC的登录实现,它可能会关闭JFrame,但不会关闭JVM。如果需要,System.exit(0);会有轻微的不同-登录“窗口”应基于
JDialog
,这允许从用户收集信息,同时在程序可见时停止执行。然后应进行身份验证,并决定从何处开始。您所知道的最大问题是,您有两个窗口,它们连接到事件调度线程,即使其中一个窗口不可见,它也会确保EDT不会终止,JVM将继续运行,请参见