1.窗体(QWidget、QMainWindow、QDialog)之间的区别
QWidget类是所有用户界面对象的基类。窗口部件是用户界面的一个原子:它从窗口系统接收鼠标、键盘和其它事件,并且在屏幕上绘制自己的表现。每一个窗口部件都是矩形,并且它们按Z轴顺序排列的。一个窗口部件可以被它的父窗口部件或者它前面的窗口部件盖住一部分。
QMainWindow 类提供一个有菜单条、锚接窗口(例如工具条)和一个状态条的主应用程序窗口。主窗口通常用在提供一个大的中央窗口部件(例如文本编辑或者绘制画布)以及周围菜单、工具条和一个状态条。QMainWindow常常被继承,因为这使得封装中央部件、菜单和工具条以及窗口状态变得更容易。继承使创建当用户点击菜单项或者工具条按钮时被调用的槽成为可能。你也可以使用Qt设计器来创建主窗口。
QDialog类是对话框窗口的基类。对话框窗口是主要用于短期任务以及和用户进行简要通讯的顶级窗口。QDialog可以是模式的也可以是非模式的。QDialog支持扩展性并且可以提供返回值。它们可以有默认按钮。QDialog也可以有一个QSizeGrip在它的右下角,使用setSizeGripEnabled()。
QDialog 是最普通的顶级窗口。不被嵌入到一个父窗口部件的窗口部件被叫做顶级窗口部件。通常情况下,顶级窗口部件是有框架和标题栏的窗口(尽管如果使用了一定的窗口部件标记,创建顶级窗口部件时也可能没有这些装饰)。在Qt中,QMainWindow和和不同的QDialog的子类是最普通的顶级窗口。
如果是顶级对话框,那就基于QDialog创建,如果是主窗体,那就基于QMainWindow,如果不确定,或者有可能作为顶级窗体,或有可能嵌入到其他窗体中,则基于QWidget创建。当然了,实际中,你还可以基于任何其他部件类来派生。看实际需求了,比如QFrame、QStackedWidget等等。
全局变量是一个使用有争议的变量。首先,全局变量方便了变量之间的共享。但同时也带来了许多问题:降低了函数或模块之间的通用性,不同的函数或模块都要依赖于全局变量。比如不同模块之间都可以自由的访问全局变量,可能会导致全局变量的不可预知性,当程序猿A修改了全局变量global_x的值,可能其他使用全局变量的地方就会出现错误,然而这种错误往往是很难发现和更正的。所以,我们应该尽量避免使用全局变量,但是全局变量的好处也是很明显的,所以某些时候全局变量能够解决局部变量很难解决的问题,所以要合理使用全局变量。
全局变量的使用有2中方式。第一种方式为:声明法,把要定义的全局变量直接定义在所使用文件的开始;第二种方法为:模块法,把要定义的全局变量单独定义在一个文件中,这种方法适用于不同文件之间的变量共享。下面对这两种方式分别进行讲解:
(1).声明法(直接定义在所使用文件的开始)
使用方法:首先在所使用的文件开头定义全局变量variable;然后在具体的使用函数中进行全局变量说明: global variable,因为只有在函数内经过说明的全局变量才能使用,否则系统将该变量视为局部变量。
注:将全局变量大写便于识别,eg:CONSTANT = 0
eg:
#test1.py CONSTANT = 0 #定义全局变量def modifyConstant() : global CONSTANT #全局变量的声明 print CONSTANT CONSTANT += 1 return if __name__ == '__main__' : modifyConstant() print CONSTANT #在主函数中使用全局变量
(2).模块法(推荐使用这种方法)
使用方法:将需要定义的全局变量单独定义在一个文件中,当使用全局变量的时候,只需将该文件给import进来即可。
eg:
#全局变量所在文件的定义#global_test1.py gl_1 = 'hello' gl_2 = 'world' 在其它模块test2.py中使用 #test2.py import global_test1 def hello_world() print global_test1.gl_1, global_test1.gl_2 def fun1() global_test1.gl_1 = 'HELLO' global_test1.gl_2 = 'WORLD' if __name__ == '__main__' : fun1() hello_world()
3.图片的设置
pyqt中如果想要在窗体中添加图片,首先需要在Qt Designer中的资源浏览器中,添加图片资源,具体过程如下:点击“编辑资源”,点击“新建资源文件”,点击添加“前缀”,点击添加“文件”,将图片添加进去。然后,添加一个label元素,点击右键,选择“更改样式表”,选择“添加资源”,就为窗体成功添加了一张图片。
添加图片成功之后,在Eric中的Project-Viewer中的第三个tab,即“Resources”tab中可以看到添加的图片资源,以“*.qrc”形式命名的。右键点击该资源,选择“Compile resource”,即编译资源,之后运行,图片才能正常显示。无图无真相,下面给出2张图片,一目了然:
左侧的图为资源浏览器,在这里添加图片资源;右侧的图为Eric中添加图片资源后的,通过“Compile resource”进行编译资源。
总结:pyqt中图片的添加需要以资源的形式添加,当添加完资源之后,还需要将资源进行编译才能正常使用。
4.主窗体弹出一个对话框
主窗体弹出对话框,我花费了一上午才搞定。下面给出代码,重要的地方我都给出了注释:
# -*- coding: utf-8 -*-"""Module implementing MainWindow."""from PyQt4.QtGui import QMainWindow from PyQt4.QtCore import pyqtSignaturefrom Ui_MainWindow import Ui_MainWindow # UI_MainWindow是主窗体的界面from Ui_ValidateWidget import * # UI_ValidateWidget是验证码对话框的界面类#ValidateDialog类是将验证码对话框进行封装。验证码对话框的事件全部都是#采用动态事件绑定到按钮上的。因为如果采用在对话框的实现类里定义事件的话,当从主窗体MainWindow跳转到#验证码对话框时,对话框的实现类里的事件是不执行的。但是当只执行验证码对话框时,其实现类里的事件是执行的。所以,#我们这里采用在MainWindow里动态绑定元素和事件的方法。说明如下:class ValidateDialog(QtGui.QDialog): username='' password='' validate_num = '' #存放用户输入的验证码 def __init__(self, ui, username, password): self.username=username; self.password=password; QtGui.QDialog.__init__(self) self.ui=ui; ui.setupUi(self); #动态绑定验证码对话框的pushBtnConfirm按钮的clicked()事件,到该类的confirm方法上 QtCore.QObject.connect(self.ui.pushBtnConfirm, QtCore.SIGNAL("clicked()"), self.confirm) def confirm(self): #该类的成员接受验证码对话框的用户输入的验证码的值 self.validate_num = self.ui.lineEditValidateNum.text() class MainWindow(QMainWindow, Ui_MainWindow): """ Class documentation goes here. """ def __init__(self, parent = None): """ Constructor """ QMainWindow.__init__(self, parent) self.setupUi(self) @pyqtSignature("") def on_pushButton_clicked(self): """ Slot documentation goes here. """ # TODO: not implemented yet #raise NotImplementedError validate_ui = Ui_Form() validate_window = ValidateWindow(validate_ui,"zhao", "sean") validate_window.exec_() #将获取到的验证码的值,显示在主窗口的界面上 self.label.setText(validate_window.validate_num) #通过登陆对话框的类直接访问其验证码的数值if __name__ == '__main__': import PyQt4, sys app = PyQt4.QtGui.QApplication(sys.argv) mainWin = MainWindow() mainWin.show() sys.exit(app.exec_())5.文字链接按钮和QTreeWidget
(1)文字链接按钮的实现
PyQt中没有像.NET那样的文字链接的按钮,但是如果想实现这种效果:点击一个具有下划线的文字,就执行一个事件,该如何实现呢?这需要通过QLabel实现,首先将QLabel的文本设置为<a></a>的内容,即:self.label_1.setText(u"<a href=‘’>监控</a>")。然后为其绑定事件:LinkActivated事件,即QtCore.QObject.connect(self.label_1,QtCore.SIGNAL("linkActivated(QString)"),self.monitor)。
(2)QTreeWidget实现
该控件用来显示树形菜单,可以通过图形界面编辑该控件中的内容,编辑好内容后,我们可以动态绑定事件给具体的子项,即:QtCore.QObject.connect(self.treewidget,QtCore.SIGNAL("itemClicked(QTreeWidgetItem*,int)",self.data_query))。
两者的代码,下面一块给出,读者可以自行查找相关的代码。
class MainWindow(QMainWindow, Ui_MainWindow): """ Class documentation goes here. """ def __init__(self, parent = None): """ Constructor """ QMainWindow.__init__(self, parent) self.setupUi(self) #设置tool box颜色 self.page_1.setStyleSheet("background-color: rgb(255, 255, 255);") self.page_2.setStyleSheet("background-color: rgb(255, 255, 255);") self.page_3.setStyleSheet("background-color: rgb(255, 255, 255);") self.page_4.setStyleSheet("background-color: rgb(255, 255, 255);") #设置label为链接文本 self.label_1.setText(u"<a href = ‘’>监控</a>") self.label_2.setText(u"<a href = ‘’>查询</a>") self.label_3.setText(u"<a href = ‘’>监控</a>") #元素和事件的动态绑定,将QLabel和事件linkActivated绑定,具体的执行函数为monitor QtCore.QObject.connect(self.label_1, QtCore.SIGNAL("linkActivated(QString)"), self.monitor) QtCore.QObject.connect(self.treeWidget, QtCore.SIGNAL("itemClicked(QTreeWidgetItem*,int)"), self.data_query) #将QTreeWidet的子项目和data_query进行绑定 #监控 def monitor(self): quit_msg = u"QLabel?" reply = QtGui.QMessageBox.question(self, u'提示', quit_msg, QtGui.QMessageBox.Yes, QtGui.QMessageBox.No) ; #数据查询 def data_query(self, item, column): if item == self.treeWidget.topLevelItem(0).child(2): quit_msg = u"treeWidget?" reply = QtGui.QMessageBox.question(self, u'提示', quit_msg, QtGui.QMessageBox.Yes, QtGui.QMessageBox.No) ;