QWindow实际上是在QWidget基础上派生出,自带了菜单栏,工具栏,状态栏等等的一个复杂的QWidget
创建项目
首先,创建项目时,从原来的QWidget变更为QMainWindow
菜单栏
获取菜单栏
QMainWindow自带一个菜单栏,通过其成员函数menuBar()可获得到菜单栏的对象指针。
菜单栏的类为QMenuBar,需要在开头include它,然后在MainWindow构造函数里写
QMenuBar *mBar=menuBar();
添加菜单
QMenuBar菜单栏中可以添加菜单,使用QmenuBar对象中的addMenu成员函数,它返回一个QMenu对象指针。
QMenu *pFile=mBar->addMenu("文件");
添加菜单项
QMenu菜单中可以添加菜单项,使用QMenu对象中的addAction成员函数,它返回一个QAction对象指针
QAction *pNew=pFile->addAction("新建");
添加菜单项的触发事件
connect(pNew,&QAction::triggered,[=](){
qDebug("新建被按下");
});
注意lambda表达式需要在配置文件中写入CONFIG += C++11
运行结果:
当我们按下新建时,将触发控制台输出代码如下,
添加分割线
pFile->addSeparator();//添加分割线
更简单的菜单项添加
connect(pFile->addAction("打开"),&QAction::triggered,[=](){
dDebug("打开被按下");
});
上述代码可一步添加菜单项并绑定信号和槽函数。
工具栏
如下如,上面是菜单栏,下面则是工具栏
一般地,一个程序中菜单栏唯一,工具栏不唯一,所以在QWindow中,自带成员函数addToolBar可自由添加工具栏
添加工具栏
QToolBar *toolBar=addToolBar("toolBar");
添加菜单项
toolBar->addAction(pNew);
由此可以看出,工具栏和菜单项类似,也可添加动作
添加按钮
QPushButton *b=new QPushButton(this);
b->setText("^_^");
toolBar->addWidget(b);
connect(b,&QPushButton::pressed,[=](){
b->setText("2333");
});
connect(b,&QPushButton::released,[=](){
b->setText("^_^");
});
效果如下图,当按下按钮时,按钮文字便为2333,松手时复原
状态栏
如图,状态栏(QStatusBar)一般是程序窗口最下方的一栏,在QWindow中,通过其成员函数statusBar()获得到
获取状态栏
QStatusBar *sBar=statusBar();
添加控件
QStatusBar *sBar=statusBar();
QLabel *label=new QLabel(this);
label->setText("这是状态栏上的第一个标签 ");
//addWidget从左往右添加控件
sBar->addWidget(label);
sBar->addWidget(new QLabel("第二个标签",this));
//addPermanentWidget从右往左添加控件
sBar->addPermanentWidget(new QLabel("第三个",this));
运行效果如下
核心控件
核心控件为主要显示的控件内容,如添加一个文本编辑框可以使用如下代码
QTextEdit *textEdit=new QTextEdit(this); //创建一个文本编辑框
setCentralWidget(textEdit);//设置窗口的中心组建
如下图,此时创建了一个文本编辑框
浮动窗口
//一个浮动窗口
QDockWidget *dock=new QDockWidget(this);
//添加这个浮动窗口
addDockWidget(Qt::RightDockWidgetArea,dock);
//向浮动窗口再添加一个文本框
QTextEdit *textEdit1=new QTextEdit(this);
dock->setWidget(textEdit1);
如下下图,浮动窗口可嵌入主窗口的上下左右
浮动窗口还可分离为独立窗口
对话框(QDialog)
对话框有模态对话框和非模态对话框之分,
模态对话框在显示时,其父窗口无法进行任何操作
非模态对话框显示时,其父窗口仍可进行操作
模态对话框
如下代码可添加一个模态对话框,
QMenu *pDialogMenu=mBar->addMenu("对话框");
connect(pDialogMenu->addAction("模态对话框"),&QAction::triggered,[=](){
qDebug("模态对话框打开");
QDialog dig;
dig.exec();
qDebug("模态对话框关闭");
});
此时,我们无法操作主窗口
非模态对话框
对于非模态对话框,直接调用其show()函数便可以显示一个独立的对话框了,但是如果我们把上述代码的exec改成show,我们发现对话框根本就没有弹出,这是因为lambda表达式在执行完毕后,自动将表达式内的所有变量自动回收,即生命周期结束。
一种方法是把对话框定义在lambda表达式之外,
还有一种方法是把对话框使用指针和new来动态分配空间定义。
如下代码,动态定义了一个非模态对话框并显示。
connect(pDialogMenu->addAction("非模态对话框"),&QAction::triggered,[=](){
qDebug("非模态对话框");
QDialog *dig=new QDialog();
dig->show();
qDebug("模态对话框已显示");
});
上述代码运行可发现,点击非模态对话框后,控制台将直接输出
非模态对话框
模态对话框已显示
由此可知,show方法不会阻塞,而exec方法会阻塞
如果使用动态内存分配的对话框,关闭时并不会内存回收,我们需要做标记如下,当对话框关闭时,自动delete对话框对象.
dig->setAttribute(Qt::WA_DeleteOnClose);
标准对话框
Qt中自带了以下几种标准对话框
使用如下代码分别查看各个对话框的样式
QMenu *pHelpMenu=mBar->addMenu("帮助");
connect(pHelpMenu->addAction("about"),&QAction::triggered,[=](){
QMessageBox::about(this,"about","OK");
});
connect(pHelpMenu->addAction("aboutQt"),&QAction::triggered,[=](){
QMessageBox::aboutQt(this,"aboutQt");
});
connect(pHelpMenu->addAction("critical"),&QAction::triggered,[=](){
QMessageBox::critical(this,"critical","This is a critical");
});
connect(pHelpMenu->addAction("information"),&QAction::triggered,[=](){
QMessageBox::information(this,"information","This is an information");
});
connect(pHelpMenu->addAction("question"),&QAction::triggered,[=](){
QMessageBox::question(this,"question","This is a question");
});
connect(pHelpMenu->addAction("warning"),&QAction::triggered,[=](){
QMessageBox::warning(this,"warning","This is a warning");
});
运行结果如下,
根据第一幅图中的说明定义,可看出除了about开头的方法外,其余方法调用后均返回一个StandardButton,我们可以根据返回值判断用户点击的按钮
如下图为问题对话框(question)中的选择分支代码,
connect(pHelpMenu->addAction("question"),&QAction::triggered,[=](){
int select=QMessageBox::question(this,"question","This is a question");
switch(select){
case QMessageBox::Yes:
qDebug("Yes");
break;
case QMessageBox::No:
qDebug("No");
break;
default:
break;
}
});
如下图,此时我们点击两个按钮,可相应打印debug信息.
文件对话框
QFileDialog::getOpenFileName函数可打开一个文件对话框
参数分别为:
- 父控件对象指针
- 对话框标题
- 初始文件路径
- 文件类型
connect(pDialogMenu->addAction("文件对话框"),&QAction::triggered,[=](){
qDebug("文件对话框打开");
QString path=QFileDialog::getOpenFileName(this,"open","../",
"Images (*.png *.xpm *.jpg);;"
"Text files (*.txt);;"
"XML files (*.xml)");
qDebug("选中路径:");
qDebug()<<path;
qDebug("文件对话框关闭");
});
对话框启动后,效果如下
且控制台输出如下:
文件对话框打开
选中路径:
"D:/qt-workspace/Example/ExampleFile.xml"
文件对话框关闭
注意:
如上代码,QFileDialog::getOpenFileName函数中的第四个参数,为文件类型过滤器,可以使用C++的一个语法糖自动拼接字符串实现多行文本