经常有初学者搞不清楚如何在PyQt中弹出对话框,以及如何处理返回值。这篇文章会举例说明,界面采用手工编写。

我们一般说的对话框指的是模态对话框(Modal Dialogue Box),一旦弹出,就不能对话框以外的窗口进行操作,必须先关闭对话框。

在PyQt中我们一般从QDialog继承创建一个类来操作,根据exec_()方法的返回值判断用户是【确定】还是【取消】了,当然也可以其他返回值,具体看文档。

这个例子创建一个主窗口,有一个表格,记录用户姓名和年龄,一个【添加】按钮,点击弹出对话框,用户输入姓名和年龄,点击【确定】返回,在主窗体表格中插入一行数据。

创建主窗体

为了方便起见使用QWdiget创建主窗体,当然你可以使用QMainWindow,用QTableView和QStandardItemModel来创建表格。

class MainWindow(QtGui.QWidget):
def __init__(self, parent=None):
QtGui.QMainWindow.__init__(self, parent)

# 创建table和model
table = QtGui.QTableView(parent=self)
self.model = QtGui.QStandardItemModel(parent=self)
self.model.setHorizontalHeaderLabels((u'姓名', u'年龄'))
table.setModel(self.model)

# 创建添加按钮
button = QtGui.QPushButton(u'添加', parent=self)

# 添加信号槽
button.clicked.connect(self.add)

# 创建一个垂直布局,用于防止表格和按钮
layout = QtGui.QVBoxLayout()
layout.addWidget(table)
layout.addWidget(button)

self.setLayout(layout)

def add(self):
pass
创建对话框

对话框从QDialog继承,按钮这里使用QButtonBox来创建,用QButtonBox的好处是创建方便,定义参数即可,并且会自动根据不同平台显示按钮的位置,和各平台风格保持一致,当然默认是英文的,你可以通过国际化来做成中文的。

这里没有做对话框内容的验证,你可以覆盖QDialog的accept方法来进行验证。

下面是对话框的创建代码,为了方便获取姓名和年龄变量,我写了两个方法供外部调用。

class Dialog(QtGui.QDialog):
def __init__(self, parent=None):
QtGui.QDialog.__init__(self, parent)
self.resize(240, 200)

# 表格布局,用来布局QLabel和QLineEdit及QSpinBox
grid = QtGui.QGridLayout()

grid.addWidget(QtGui.QLabel(u'姓名', parent=self), 0, 0, 1, 1)

self.leName = QtGui.QLineEdit(parent=self)
grid.addWidget(self.leName, 0, 1, 1, 1)

grid.addWidget(QtGui.QLabel(u'年龄', parent=self), 1, 0, 1, 1)

self.sbAge = QtGui.QSpinBox(parent=self)
grid.addWidget(self.sbAge, 1, 1, 1, 1)

# 创建ButtonBox,用户确定和取消
buttonBox = QtGui.QDialogButtonBox(parent=self)
buttonBox.setOrientation(QtCore.Qt.Horizontal) # 设置为水平方向
buttonBox.setStandardButtons(QtGui.QDialogButtonBox.Cancel|QtGui.QDialogButtonBox.Ok) # 确定和取消两个按钮
# 连接信号和槽
buttonBox.accepted.connect(self.accept) # 确定
buttonBox.rejected.connect(self.reject) # 取消

# 垂直布局,布局表格及按钮
layout = QtGui.QVBoxLayout()

# 加入前面创建的表格布局
layout.addLayout(grid)

# 放一个间隔对象美化布局
spacerItem = QtGui.QSpacerItem(20, 48, QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
layout.addItem(spacerItem)

# ButtonBox
layout.addWidget(buttonBox)

self.setLayout(layout)

def name(self):
return self.leName.text()

def age(self):
return self.sbAge.value()
编写对话框调用代码

调用对话框只要使用exec_方法即可,它会弹出对话框并根据用户操作返回值,根据返回值判断是【确定】还是【取消】。

dialog = Dialog(parent=self)
if dialog.exec_():
self.model.appendRow((
QtGui.QStandardItem(dialog.name()),
QtGui.QStandardItem(str(dialog.age())),
))

dialog.destroy()
完整代码和截图

# -*- coding: utf-8 -*-
from PyQt4 import QtGui, QtCore

class MainWindow(QtGui.QWidget):
def __init__(self, parent=None):
QtGui.QMainWindow.__init__(self, parent)

# 创建table和model
table = QtGui.QTableView(parent=self)
self.model = QtGui.QStandardItemModel(parent=self)
self.model.setHorizontalHeaderLabels((u'姓名', u'年龄'))
table.setModel(self.model)

# 创建添加按钮
button = QtGui.QPushButton(u'添加', parent=self)

# 添加信号槽
button.clicked.connect(self.add)

# 创建一个垂直布局,用于防止表格和按钮
layout = QtGui.QVBoxLayout()
layout.addWidget(table)
layout.addWidget(button)

self.setLayout(layout)

def add(self):
dialog = Dialog(parent=self)
if dialog.exec_():
self.model.appendRow((
QtGui.QStandardItem(dialog.name()),
QtGui.QStandardItem(str(dialog.age())),
))

dialog.destroy()

class Dialog(QtGui.QDialog):
def __init__(self, parent=None):
QtGui.QDialog.__init__(self, parent)
self.resize(240, 200)

# 表格布局,用来布局QLabel和QLineEdit及QSpinBox
grid = QtGui.QGridLayout()

grid.addWidget(QtGui.QLabel(u'姓名', parent=self), 0, 0, 1, 1)

self.leName = QtGui.QLineEdit(parent=self)
grid.addWidget(self.leName, 0, 1, 1, 1)

grid.addWidget(QtGui.QLabel(u'年龄', parent=self), 1, 0, 1, 1)

self.sbAge = QtGui.QSpinBox(parent=self)
grid.addWidget(self.sbAge, 1, 1, 1, 1)

# 创建ButtonBox,用户确定和取消
buttonBox = QtGui.QDialogButtonBox(parent=self)
buttonBox.setOrientation(QtCore.Qt.Horizontal) # 设置为水平方向
buttonBox.setStandardButtons(QtGui.QDialogButtonBox.Cancel|QtGui.QDialogButtonBox.Ok) # 确定和取消两个按钮
# 连接信号和槽
buttonBox.accepted.connect(self.accept) # 确定
buttonBox.rejected.connect(self.reject) # 取消

# 垂直布局,布局表格及按钮
layout = QtGui.QVBoxLayout()

# 加入前面创建的表格布局
layout.addLayout(grid)

# 放一个间隔对象美化布局
spacerItem = QtGui.QSpacerItem(20, 48, QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
layout.addItem(spacerItem)

# ButtonBox
layout.addWidget(buttonBox)

self.setLayout(layout)

def name(self):
return self.leName.text()

def age(self):
return self.sbAge.value()

if __name__ == '__main__':
import sys
app = QtGui.QApplication(sys.argv)
mainWindow = MainWindow()
mainWindow.show()
sys.exit(app.exec_())

PyQt中弹出对话框操作的更多相关文章

  1. Swing中弹出对话框的几种方式_JOptionPane.showMessageDialog等详解

    Swing中弹出对话框的几种方式_JOptionPane.showMessageDialog等详解   在swing中,基于业务的考量,会有对话框来限制用户的行为及对用户的动作进行提示. Swing中 ...

  2. Android中弹出对话框,AlertDialog关键代码

    写在这里便于以后查看. Android中弹出对话框的关键代码: btn01.setOnClickListener(new OnClickListener() { @Override public vo ...

  3. 在动态链接库dll中弹出对话框

    在动态链接库dll中弹出对话框步骤: 1.添加Dialog资源,然后在资源视图的对话框界面右击添加类,输入类名MyDlg,使得其继承与CDialogEx.(继承CDialog应该也可以)2.在新生成的 ...

  4. 在MFC主对话框OnInitDialog()中弹出对话框

    BOOL CXXXDlg::OnInitDialog(){ CDialogEx::OnInitDialog(); SetIcon(m_hIcon, TRUE); SetIcon(m_hIcon, FA ...

  5. Android 在Service中弹出对话框

    1.在Androidmanifest.xml中插入 <uses-permission android:name="android.permission.SYSTEM_ALERT_WIN ...

  6. 引用dll动态库,动态库中弹出对话框输入,将输入参数,作为变量继续调用。

    在做支付项目时,引用动态库,动态库弹出支付宝或者微信的支付码,继而接收.最终将结果返回给调用动态库方法. 首先,动态库接收的是一个string 类型的xml,如 public string Pay(s ...

  7. Swing中弹出对话框的几种方式(转)

    http://www.cnblogs.com/mailingfeng/archive/2011/12/28/2304289.html 在swing中,基于业务的考量,会有对话框来限制用户的行为及对用户 ...

  8. jeecg3.7中弹出窗操作标签dgOpenOpt的用法

    1.基本参数 参数名                    描述 url                           弹出页面地址 title                         ...

  9. Java中弹出对话框中的几种方式

    1.显示一个错误对话框,该对话框显示的 message 为 'alert': JOptionPane.showMessageDialog(null, "alert", " ...

随机推荐

  1. PhoneGap笔记-01 基本使用

    1. 环境配置 1.1 常用框架 jQuery Backbone.js dojo bootstrap kendo UI Sencha jQuery Mobile PhoneJS AngularJS I ...

  2. IOS 取值控件(UIPicker)的使用方法

    1.简单地取值控件示例 我们要做的一个UITextFiled,当点击UITextFiled,出现一个UIPick取值的页面,可以选择性别,在viewDidLoad中写下 //sexPicker UIP ...

  3. 数据结构之后缀数组suffix array

    在字符串处理当中,后缀树和后缀数组都是非常有力的工具,其中后缀树大家了解得比较多,关于后缀数组则很少见于国内的资料.其实后缀是后缀树的一个非常精巧的替代品,它比后缀树容易编程实现,能够实现后缀树的很多 ...

  4. 17.1.1.9 Introducing Additional Slaves to an Existing Replication Environment 引入额外的Slaves 到一个存在的复制

    17.1.1.9 Introducing Additional Slaves to an Existing Replication Environment 引入额外的Slaves 到一个存在的复制环境 ...

  5. 分区 Service Bus 队列和主题

    编辑人员注释:本文章由 Windows Azure Service Bus 团队的二级项目经理 Ruppert Koch 撰写. 上周,Microsoft 发布了 Azure SDK 2.2 和 Se ...

  6. Linux BFS简介

    1. 什么是BFS 这里的BFS可不是广度优先算法,本文介绍的BFS是Linux的一个非Linux mainline调度算法.根据作者的描述BFS能够极大的提高低端设备(这里的低端设备的定义为:CPU ...

  7. FastReport配置打印预览button_C++

    如需转载请标明出处:http://blog.csdn.net/itas109 FastReport採用C++方式.配置打印预览选项 //打印预览 //配置打印预览选项 pReport->Prev ...

  8. js字符串大小写转换

    var str = 'hello world'; alert(str.toUpperCase());//将字符串转换为大写. alert(str.toLowerCase());//将字符串转换为小写. ...

  9. 【在网页中获取截图数据】Chrome和Firefox下的实战经验

    [转载自我在segmentfault的专栏:https://segmentfault.com/a/1190000004584071] 最近在实现一个功能,需求如下: 前提:当前页面无弹窗 页面任意位置 ...

  10. DBNull

    1. Null不是0.不是空,是"不知道".数据库中int是可以为null的,但是C#中int不可以为null,存在一个不匹配的问题. 2. 介绍"可控数据类型" ...