我知道有人问过这个问题,但我没有找到解决方案。
我为登录创建了一个 JFrame
,我想在按下“Cont Nou”按钮后用新帐户的 jpanel 打开一个新窗口,但不知道如何设置初始框架消失并出现带有 jpanel 的框架。你有什么想法吗?谢谢你!
这是我到目前为止所做的:
这是带有登录名的 JFrame
:
public class LogIn extends JFrame implements ActionListener{
private JLabel labelEmail;
private JLabel labelParola;
private JTextField textFieldEmail;
private JPasswordField textFieldParola;
private JButton buttonLogin;
private JButton buttonContNou;
public LogIn (){
super();
this.setSize(400,200);
this.setTitle("Login");
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
this.setLayout(null);
this.setResizable(false);
this.setupComponents();
}
private void setupComponents(){
labelEmail = new JLabel("Email: ");
labelParola = new JLabel("Parola: ");
textFieldEmail = new JTextField();
textFieldParola = new JPasswordField();
buttonContNou = new JButton("Cont Nou");
buttonLogin = new JButton("Login");
labelEmail.setBounds(30,30,50,20);
labelParola.setBounds(30,70,50,20);
textFieldEmail.setBounds(100,30,185,20);
textFieldParola.setBounds(100,70,185,20);
buttonContNou.setBounds(185,110,100,20);
buttonLogin.setBounds(100,110,75,20);
buttonLogin.addActionListener(this);
buttonContNou.addActionListener(this);
this.add(labelEmail);
this.add(labelParola);
this.add(textFieldEmail);
this.add(textFieldParola);
this.add(buttonLogin);
this.add(buttonContNou);
}
public static void main(String[] args){
LogIn login= new LogIn();
login.setVisible(true);
}
@Override
public void actionPerformed(ActionEvent e) {
if(e.getSource().equals(buttonLogin)){
boolean toateDateleOk =true;
textFieldEmail.setBackground(Color.WHITE);
textFieldParola.setBackground(Color.WHITE);
if(textFieldEmail.getText().length()==0){
textFieldEmail.setBackground(Color.RED);
toateDateleOk =false;
}
if(textFieldParola.getPassword().length==0){
textFieldParola.setBackground(Color.RED);
toateDateleOk =false;
}
if(!toateDateleOk)
return ;
else
System.out.println("Incepe Procesul de logare");
if(e.getSource().equals(buttonContNou)){
//this.dispose();
//dispose();
//new NewAccountPanel().setVisible(true);
//new secondTab().show();
}
}
}
}
让我们开始吧,您应该尽可能避免直接从顶级容器扩展,例如 JFrame
。这将您束缚在单一用途的组件上,例如,您不能在另一个窗口(作为大型组件层次结构的一部分)或小程序上下文中重复使用登录控件。您也没有向类本身添加任何新功能。
您还应该限制向用户推送的窗口数量,因为它很快就会变得困惑。看看The Use of Multiple JFrames, Good/Bad Practice?了解更多详情。
相反,您应该考虑使用 MVC (Model-View-Controller) 设计来减少类之间的耦合量以及组件暴露于未经授权/不需要的修改。
契约(Contract)( View )
让我们从定义契约开始,这定义了流程中的每个元素可以做什么和期望做什么以及传递的信息
查看
这定义了应用程序中每个 View 的核心功能。每个 View 都可以有一个 Controller (由 C
定义),并期望提供一个 JComponent
作为基本表示,用于将 View 物理添加到 容器
public interface View<C> {
public JComponent getView();
public void setController(C controller);
public C getController();
}
登录 View
这定义了登录 View 期望提供的信息,在这个例子中,我们提供了用户名和密码信息以及 Controller 可以告诉 View 登录尝试失败的方法。这允许 View 重置 View 并在需要时显示错误消息
public interface LoginView extends View<LoginController> {
public String getUserName();
public char[] getPassword();
public void loginFailed(String errorMessage);
}
登录 Controller
这定义了登录 View 的 Controller 预期发生的预期操作, View 调用它来告诉 Controller 它应该做某事...
public interface LoginController {
public void performLogin(LoginView view);
public void loginCanceled(LoginView view);
}
应用 View
我没有提供这方面的示例,但您可以想象您需要提供您可能希望提供的详细信息,以便感兴趣的各方从 View 中提取详细信息。
实现
登录面板
这是基本的 LoginView
实现...
public class LoginPane extends JPanel implements LoginView {
private JTextField userName;
private JPasswordField password;
private JButton okButton;
private JButton cancelButton;
private LoginController controller;
public LoginPane() {
setLayout(new GridBagLayout());
userName = new JTextField(10);
password = new JPasswordField(10);
okButton = new JButton("Ok");
cancelButton = new JButton("Cancel");
GridBagConstraints gbc = new GridBagConstraints();
gbc.gridx = 0;
gbc.gridy = 0;
gbc.insets = new Insets(2, 2, 2, 2);
gbc.anchor = GridBagConstraints.WEST;
add(new JLabel("User name: "), gbc);
gbc.gridy++;
add(new JLabel("Password: "), gbc);
gbc.gridx = 1;
gbc.gridy = 0;
gbc.gridwidth = 2;
add(userName, gbc);
gbc.gridy++;
add(password, gbc);
gbc.gridwidth = 1;
gbc.gridy++;
add(okButton, gbc);
gbc.gridx++;
add(cancelButton, gbc);
okButton.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
getController().performLogin(LoginPane.this);
}
});
cancelButton.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
getController().loginCanceled(LoginPane.this);
}
});
}
@Override
public String getUserName() {
return userName.getText();
}
@Override
public char[] getPassword() {
return password.getPassword();
}
@Override
public void loginFailed(String errorMessage) {
JOptionPane.showMessageDialog(this, errorMessage, "Login failed", JOptionPane.ERROR_MESSAGE);
}
@Override
public void setController(LoginController controller) {
this.controller = controller;
}
@Override
public JComponent getView() {
return this;
}
@Override
public LoginController getController() {
return controller;
}
}
应用面板
基本应用View
public class ApplicationPane extends JPanel implements View {
public ApplicationPane() {
setLayout(new GridBagLayout());
add(new JLabel("Welcome to my awesome application"));
}
@Override
public JComponent getView() {
return this;
}
@Override
public void setController(Object controller) {
// What ever controller you want to use...
}
@Override
public Object getController() {
throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
}
}
把它们放在一起......
我们会的,这是很多信息,但您如何使用它?
public class CoreApplicationCPane extends JPanel {
protected static final String LOGIN_VIEW = "View.login";
protected static final String APPLICATION_VIEW = "View.application";
private LoginView loginView;
private ApplicationPane applicationView;
private CardLayout cardLayout;
public CoreApplicationCPane() {
cardLayout = new CardLayout();
setLayout(cardLayout);
loginView = new LoginPane();
applicationView = new ApplicationPane();
add(loginView.getView(), LOGIN_VIEW);
add(applicationView.getView(), APPLICATION_VIEW);
loginView.setController(new LoginController() {
@Override
public void performLogin(LoginView view) {
// Do what ever you need to do...
String name = view.getUserName();
char[] password = view.getPassword();
//...
cardLayout.show(CoreApplicationCPane.this, APPLICATION_VIEW);
}
@Override
public void loginCanceled(LoginView view) {
SwingUtilities.windowForComponent(CoreApplicationCPane.this).dispose();
}
});
cardLayout.show(this, LOGIN_VIEW);
}
}
这基本上就是所有东西连接在一起的地方。 LoginView
和 ApplicationView
被实例化并添加到主视图, Controller 被插入。
看看:
了解更多详情。
有关更详细的示例,请查看 Java and GUI - Where do ActionListeners belong according to MVC pattern?