虽然 Nokia 刚刚宣布和微软合做,推出 WP7 的智能手机,如今 IT 界依然一片哗然(不过也是在乎料之中),但这并不会影响咱们对于 Qt 的兴趣。好了,如今咱们来看的是关于 QDialog 的一些东西。ide
首先先来看 QDialog 的一副截图(出自 Qt Developer Day, 2009):函数
在这里,咱们要注意的是不一样平台之上对话框的按钮的不一样。其实这是同一段代码编译的,没有使用条件编译技术。那么是如何作到的呢?答案是使用 QDialogButtonBox 这个类。布局
QDialogButtonBox 用于管理对话框按钮的顺序、布局、文本和图标等,以保证这些在不一样平台可以具备不一样表现。若是咱们没有 Mac 系统,咱们怎么知道该如何布局按钮呢?咱们怎么得到这些按钮在不一样平台上的图标呢?这些都不会成为咱们实现程序的障碍,由于使用 QDialogButtonBox 就足够了。例如,要实现上面的效果,咱们只须要一行代码:this
- QDialogButtonBox box(QDialogButtonBox::Save |
- QDalogButtonBox::Discard |
- QDialogButtonBox::Cancel);
这样,Qt 就会在不一样的平台作出不一样的表现。spa
QDialogButtonBox 为不一样的按钮分配不一样的角色来实现这一功能。所以,咱们在上面的 QDialogButtonBox::Save 这些实际都是一个简单的 enum,用于标记按钮的角色。若是你须要使用本身的按钮,而且为之附加角色,那么可使用下面的代码:orm
- QDialogButtonBox box;
- box.addButton(myButton, QDialogButtonBox::AcceptRole);
这样,myButton 的角色就是 QDialogButtonBox::AcceptRole,而 QDialogButtonBox 也可以根据这个角色为之分配合适的图标和位置等等。blog
QDialogButtonBox 先告一段落,下面来讲说模态对话框。什么是模态对话框?所谓模态,就是在对话框弹出来以后,可以阻塞后面的窗口。Windows 上通常在退出时会弹出来一个问你是否保存的对话框,就是一个模态对话框。当它出现的时候,后面的窗口是不能点击的,必需要你关闭这个对话框以后才能够。在 Qt 实现模态对话框很简单:get
- MyQDialogSubclass dialog;
- // Various bits of initialization
- if (dialog.exec() == QDialog::Accept) { // HERE!!!
- // Set new values or do extra work
- // based on results.
- }
这段代码在运行时,会在标记 HERE 注释这行阻塞,具体是 QDialog::exec() 这个函数。这以后的代码在你关闭 dialog 对话框以后才会被执行。利用这一技术,你就能够在 if 里面获取依赖于对话框返回值的数据。例如,对话框用于收集用户数据等。string
- class MyDialog : public QDialog
- {
- public:
- QString name;
- };
- // ....
- MyDialog d;
- if(d.exec() == QDialog::Accept) {
- QString name = d.name;
- // do something with name...
- }
上面的代码,MyDialog 用于用户输入 name 的值。咱们使用模态对话框,就能够在 if 里面获取这个值了。it
不过,不一样平台上的模态对话框的使用方式是不同的。好比,Windows 平台上,模态对话框用于严重错误的提示,或者是在继续以前必须完成的任务;KDE 上,模态对话框用于可能形成数据丢失或者严重后果的交互。
Qt 中,对话框的打开具备三种方式:
前两种咱们很容易理解,下面来看看什么是窗口模态。好比,咱们有两个窗口(如下图示来自 Qt Developer Day, 2009):
使用以下代码,咱们用 open() 函数打开一个对话框:
- if(!messageBox) {
- messageBox = new QMessageBox("SDI",
- "The document has been modified. \n"
- "Do you want to save your changes?",
- QMessageBox::Warning,
- QMessageBox::Yes | QMessageBox::Default,
- QMessageBox::No,
- QMessageBox::Cancel | QMessageBox::Escape,
- this);
- connect(messageBox, SIGNAL(finished(int)), SLOT(handleDialogClose(int)));
- }
- messageBox->open();
看看运行的结果:
这就是 open() 函数的效果:它相似模态对话框,可是只会阻塞一个窗口,而不是将整个系统阻塞掉。
最后一个要说的技术是 QFormLayout。这个布局用于展现表单。来看一下下面的截图(出自 Qt Developer Day, 2009):
注意这里的文本对齐方式和按钮的顺序。前面已经说过用 QDialogButtonBox 实现不一样平台下按钮的顺序,而上面的对齐方式则是使用 QFormLayout 实现,例如:
- QFormLayout *layout = new QFormLayout;
- layout->addRow(tr("Name:"), nameLineEdit);
- // more...
这样,咱们又可以使用简单的代码实现不一样平台的不一样布局表现。