[英]PyQt5 Login to Register Dialog Auto Close
I have a login and register dialog, and of course a main window.我有一个登录和注册对话框,当然还有一个主要的 window。 So, I want the users to be able to switch between login and register dialog, and if the user enters correct credentials, the user can go to the main window.所以,我希望用户能够在登录和注册对话框之间切换,如果用户输入正确的凭据,用户可以 go 到主 window。 If the user registered a new credential, then the user will be redirected to the login window.如果用户注册了新的凭证,那么用户将被重定向到登录 window。 That said, the first interface that the user see is the login dialog.也就是说,用户看到的第一个界面是登录对话框。 Here are some codes for login-register dialog:以下是登录注册对话框的一些代码:
class Login(QDialog):
# Push Button -> Login
# Push Button 2 -> To Register
# Push Button 3 -> Exit
def __init__(self):
super(Login, self).__init__()
# Load Login UI
loadUi("Login.ui", self)
# Set Translucent Background for the Windows
self.setWindowFlags(PyQt5.QtCore.Qt.FramelessWindowHint)
self.setAttribute(PyQt5.QtCore.Qt.WA_TranslucentBackground)
# Set Push Button 1 to call the function upon clicked
self.pushButton.clicked.connect(self.check_login)
# Set Push Button 2 to call the function upon clicked
self.pushButton_2.clicked.connect(self.redirect_to_register)
# Set Push Button 3 to call the function upon clicked
self.pushButton_3.clicked.connect(self.close_window)
# Show the Window
self.show()
# Procedure to redirect to register windows
def redirect_to_register(self):
self.close() # Close the login windows
# Show the register windows
self.register = Register()
self.register.show()
...
class Register(QDialog):
# Push Button -> Register
# Push Button 2 -> To Login
# Push Button 3 -> Exit
def __init__(self):
# Load Register UI
super(Register, self).__init__()
loadUi("Register.ui", self)
# Set Translucent Background for the Windows
self.setWindowFlags(PyQt5.QtCore.Qt.FramelessWindowHint)
self.setAttribute(PyQt5.QtCore.Qt.WA_TranslucentBackground)
# Set Push Button 2 to call the function upon clicked
self.pushButton.clicked.connect(self.insert_to_database)
# Set Push Button 2 to call the function upon clicked
self.pushButton_2.clicked.connect(self.redirect_to_login)
# Set Push Button 3 to call the function upon clicked
self.pushButton_3.clicked.connect(self.close_window)
# Show the Window
self.show()
# Procedure to redirect to login windows
def redirect_to_login(self):
# Close the login windows
self.close()
# Show the register windows
self.login = Login()
self.login.show()
def close_window(self):
self.close()
I load the.ui file of both dialog.我加载了两个对话框的 .ui 文件。 But, for the main window, the.py file is converted from the.ui file.但是,对于主 window,.py 文件是从 .ui 文件转换而来的。 That said, in the main of the login file, I call the main window with this code:也就是说,在登录文件的主文件中,我使用以下代码调用主文件 window:
import GoodLife
# Call main
if __name__ == "__main__":
# Init App
app = QApplication(sys.argv)
QtGui.QFontDatabase.addApplicationFont("../img/dripicons-v2.ttf")
# Build the window
window = Login()
if(window.exec_() == QDialog.Accepted):
GoodLife = QMainWindow()
ui = Ui_MainWindow()
ui.setupUi(GoodLife)
GoodLife.setWindowTitle("Good Life - Your Dear Bestfriend :)")
GoodLife.setWindowIcon(QtGui.QIcon('../img/goodlife.jpg'))
GoodLife.show()
sys.exit(app.exec_())
With that code, I am able to go into the main window after logging in. But, whenever I tried to switch to register dialog, the register dialog keeps auto-closing.使用该代码,我可以在登录后将 go 进入主 window。但是,每当我尝试切换到注册对话框时,注册对话框都会自动关闭。 I believe that the line sys.exit(app.exec_())
is the cause of it, because when I unindent the line once, I can go to the register, but not the main window.我相信这行sys.exit(app.exec_())
是它的原因,因为当我取消缩进一次时,我可以 go 到寄存器,但不是主要的 window。 Can anyone help me on this?谁可以帮我这个事?
The problem is that when a dialog is closed, it exits its event loop (the one launched with exec
) with a Rejected
result.问题是,当一个对话框关闭时,它会退出它的事件循环(使用exec
启动的那个)并返回一个Rejected
结果。
In your case, since the rejection doesn't match window.exec_() == QDialog.Accepted
, the result is that that whole block is not evaluated, and the application simply exits.在您的情况下,由于拒绝与window.exec_() == QDialog.Accepted
不匹配,因此结果是未评估整个块,并且应用程序简单地退出。
A simple solution would be to hide the login until the registration is completed (or rejected) and show it again afterwards.一个简单的解决方案是在注册完成(或被拒绝)之前隐藏登录,然后再次显示。
Since the login dialog should be shown anyway, there's no need for custom signals or if statements, as it's enough to call the registration dialog's exec_ in the redirect_to_register
function, so that you can show again the login no matter the result of the registration.由于无论如何都应该显示登录对话框,因此不需要自定义信号或 if 语句,因为在redirect_to_register
function 中调用注册对话框的 exec_ 就足够了,这样无论注册结果如何,您都可以再次显示登录。
Unfortunately, there's a problem with that: in Qt, hiding a dialog results in a behavior similar to closing it (so, rejecting).不幸的是,有一个问题:在 Qt 中,隐藏对话框会导致类似于关闭它的行为(因此,拒绝)。
The solution is to avoid the base implementation of QDialog (which overrides both hide()
and setVisible()
), and use that of QWidget instead:解决方案是避免 QDialog 的基本实现(覆盖hide()
和setVisible()
),而使用 QWidget 的基本实现:
def redirect_to_register(self):
QtWidgets.QWidget.setVisible(self, False)
self.register = Register()
self.register.exec_()
self.show()
This also means that in the register dialog you should not try to recreate the login window:这也意味着在注册对话框中您不应尝试重新创建登录 window:
class Register(QDialog):
def __init__(self):
# ...
self.pushButton_2.clicked.connect(self.accept)
Some unasked suggestions:一些未提出的建议:
close_window
function if it just calls self.close()
: just connect signals to self.close
;如果只调用self.close()
,则无需实现close_window
function :只需将信号连接到self.close
;pushButton_x
is never a good idea, as you cannot easily distinguish their role;更详细地使用 object 名称,包括您在 Designer 中创建的小部件:拥有大量pushButton_x
绝不是一个好主意,因为您无法轻松区分它们的角色;../
) folders;小心相对路径,特别是对于父( ../
)文件夹; consider using Qt resource systems (which also allows you to set icons and images directly in Designer);考虑使用 Qt 资源系统(也允许您直接在 Designer 中设置图标和图像);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.