Qt学习笔记

1.一个最简单的QT应用程序

#include <QApplication>   //应用程序类
#include <QWidget>
int main(int argc, char *argv[])
{
      QApplication a(argc, argv);
      QWidget w;
      w.show();

      return a.exec();
      //程序进入消息循环,等待对用户输入进行响应。这里main()把控制权转交给Qt,Qt完成事件处理工作,当应用程序退出的时候exec()的值就会返回。在exec()中,Qt接受并处理用户和系统的事件并且把它们传递给适当的窗口部件。
}


2.信号与槽机制
2.1 connect()函数

    connect(sender, signal, receiver, slot);

参数:
·sender:发出信号的对象
·signal:发送对象发出的信号
·receiver:接收信号的对象
·slot:接收对象在接收到信号之后所需要调用的函数


2.2 代码演示(Qt5)

 // widget.cpp //
#include "widget.h"
#include <QObject>

Widget::Widget(QWidget *parent)
    : QWidget(parent)
{
    // button是widget.h里面的私有全局变量,qpushbutton类
    button.setParent(this);
    button.setText("quit");
    button.move(10,100);

    QObject::connect(&button,&QPushButton::clicked,this,&Widget::close);
}

Widget::~Widget()
{
    
}


2.3 自定义信号槽

2.3.1 实现一个窗口切换的例子:
    有一个主窗口类Widget,有一个次窗口类SubWidget。主窗口有button,可以切换次窗口。次窗口有button,切换主窗口。

主切次: 在主窗口建立从窗口的对象,connect(按钮,按下,this(主窗口),自定义处理函数),
        即:sub.show()  this.hide()
次切主:次窗口内的button发出信号,主窗口接受。即:
        connect(按钮,按下,this,自定义send函数)
        主窗口接收,即:
        connect(次窗口,次窗口发的信号,this,deal函数)    

2.3.2 代码
 // SubWidget.h //
#ifndef SUBWIDGET_H
#define SUBWIDGET_H

#include <QWidget>
#include <QPushButton>

class SubWidget : public QWidget
{
    Q_OBJECT
public:
    explicit SubWidget(QWidget *parent = 0);
    void sendSlot();
signals:
    void mySignal();
public slots:
    
private:
    QPushButton b;
};

#endif // SUBWIDGET_H

// Widget.h //
#ifndef WIDGET_H
#define WIDGET_H

#include <QWidget>
#include <QPushButton>
#include "subwidget.h"

class Widget : public QWidget
{
    Q_OBJECT
    
public:
    Widget(QWidget *parent = 0);
    void changeWin();
    void deal();
    ~Widget();
private:
    QPushButton button,button2;
    SubWidget sub;
};

#endif // WIDGET_H


// Widget.cpp //
#include "widget.h"
#include <QObject>

Widget::Widget(QWidget *parent)
    : QWidget(parent)
{
    button.setParent(this);
    button.setText("quit");
    button.move(300,100);

    QObject::connect(&button,&QPushButton::clicked,this,&Widget::close);


    button2.setParent(this);
    button2.setText("切换次窗口");
    button2.move(10,100);

    QObject::connect(&button2,&QPushButton::clicked,this,&Widget::changeWin);

    connect(&sub,&SubWidget::mySignal,this,&Widget::deal);
}

void Widget::changeWin(){
    sub.show();
    this->hide();
}

void Widget::deal(){
    sub.hide();
    this->show();
}

Widget::~Widget()
{
    
}

// SubWidget.cpp //
#include "subwidget.h"

SubWidget::SubWidget(QWidget *parent) :
    QWidget(parent)
{
    this->setWindowTitle("sub");
    b.setParent(this);
    b.setText("切换主窗口");

    connect(&b,&QPushButton::clicked,this,&SubWidget::sendSlot);

}
void SubWidget::sendSlot(){
    emit mySignal();
}


2.3.3 自定义信号槽需要注意的事项

·发送者和接收者都需要是QObject的子类;

·使用 signals 标记信号函数,信号是一个函数声明,返回 void,不需要实现函数代码;

·槽函数是普通的成员函数,作为成员函数,会受到 public、private、protected 的影响;需要和信号一致(参数,返回值);

·使用 emit 在恰当的位置发送信号;

·使用QObject::connect()函数连接信号和槽。

·任何成员函数、static 函数、全局函数和 Lambda 表达式都可以作为槽函数


 2.3.4 Lambda 表达式作为槽函数

[函数对象参数](操作符重载函数参数)mutable或exception ->返回值{函数体}


(1)函数对象参数:
    [],标识一个Lambda的开始。
    
        空。没有使用任何函数对象参数。

        =。函数体内可以使用Lambda所在作用范围内所有可见的局部变量(包括Lambda所在类的this),并且是值传递方式(相当于编译器自动为我们按值传递了所有局部变量)。

        &。函数体内可以使用Lambda所在作用范围内所有可见的局部变量(包括Lambda所在类的this),并且是引用传递方式(相当于编译器自动为我们按引用传递了所有局部变量)。

        this。函数体内可以使用Lambda所在类中的成员变量。

        a。将a按值进行传递。按值进行传递时,函数体内不能修改传递进来的a的拷贝,因为默认情况下函数是const的。要修改传递进来的a的拷贝,可以添加mutable修饰符。

        &a。将a按引用进行传递。

        a, &b。将a按值进行传递,b按引用进行传递。

        =,&a, &b。除a和b按引用进行传递外,其他参数都按值进行传递。

        &, a, b。除a和b按值进行传递外,其他参数都按引用进行传递。
(2)操作符重载函数参数;
    标识重载的()操作符的参数,没有参数时,这部分可以省略。参数可以通过按值(如:(a,b))和按引用(如:(&a,&b))两种方式进行传递。


(3)可修改标示符;
    mutable声明,这部分可以省略。按值传递函数对象参数时,加上mutable修饰符后,可以修改按值传递进来的拷贝(注意是能修改拷贝,而不是值本身)。

(4)


3 Qt窗口系统

3.1 QWidget 
所有窗口及窗口控件都是从QWidget直接或间接派生出来的。

3.2 QMainWindow

QMainWindow是一个为用户提供主窗口程序的类,包含一个菜单栏(menu bar)、多个工具栏(tool bars)、多个锚接部件(dock widgets)、一个状态栏(status bar)及一个中心部件(central widget),是许多应用程序的基础,如文本编辑器,图片编辑器等。

3.2.1 菜单栏
(1)创建菜单栏
    #include <QMenuBar>
    QMenuBar *pBar = menuBar();

(2)创建菜单
    #include <QMenu>
    QMenu *pFile = pBar->addMenu("file");


(3)添加菜单项
    #include <QAction>
    QAction *pNew = pFile->addAction("new");

    connect(pNew,&QAction::triggered,
            [](){
        qDebug() << "new file";
    });
    //分割线
    pFile->addSeparator();

3.2.2 工具栏
    直接调用QMainWindow类的addToolBar()函数获取主窗口的工具条对象,每增加一个工具条都需要调用一次该函数。

    #include <QToolBar>
    QToolBar *toolBar = addToolBar("tool");
    //工具栏添加快捷键
    toolBar->addAction(pNew);

    //添加按钮
    QPushButton *b = new QPushButton(this);
    b->setText("^^");

    toolBar->addWidget(b);    //添加
    connect(b,&QPushButton::clicked,

            [=](){
        b->setText("123");
    });

3.2.3 状态栏
    #include <QStatusBar>
    #include <QLabel>
    QStatusBar *sBar = statusBar();
    sBar->addWidget(new QLabel("1",this));

3.2.4 核心控件
    #include <QTextEdit>
    QTextEdit *textEdit = new QTextEdit(this);
    setCentralWidget(textEdit);


3.2.5 资源文件


4 对话框QDialog

对话框通常会是一个顶层窗口,出现在程序最上层,用于实现短期任务或者简洁的用户交互。

    Qt 中使用QDialog类实现对话框。就像主窗口一样,我们通常会设计一个类继承QDialog。QDialog(及其子类,以及所有Qt::Dialog类型的类)的对于其 parent 指针都有额外的解释:如果 parent 为 NULL,则该对话框会作为一个顶层窗口,否则则作为其父组件的子对话框(此时,其默认出现的位置是 parent 的中心)。

对话框分为模态对话框和非模态对话框。
    模态对话框,就是会阻塞同一应用程序中其它窗口的输入。

    QMenu *pHelp = pBar->addMenu("help");
    QAction *about = pHelp->addAction("aboout");
    connect(about,&QAction::triggered,

            [](){
        QDialog dlg;
        dlg.setWindowTitle("abcdefg");
        dlg.exec();
    });
   

    非模态对话框:
    QMenu *pm = pBar->addMenu("非模态对话框");
    QAction *pa = pm->addAction("非模块");
    connect(pa,&QAction::triggered,

            [](){
        QDialog *dlg2 = new QDialog;                //动态分配内存,setAttribute()函数设置对话框关闭时,自动销毁对话框。
        dlg2->setAttribute(Qt::WA_DeleteOnClose);
        dlg2->show();
    });    


4.1 标准对话框
    所谓标准对话框,是 Qt 内置的一系列对话框,用于简化开发。
·QColorDialog:        选择颜色;
·QFileDialog:            选择文件或者目录;
·QFontDialog:            选择字体;
·QInputDialog:        允许用户输入一个值,并将其值返回;
·QMessageBox:            模态对话框,用于显示信息、询问问题等;
·QPageSetupDialog:    为打印机提供纸张相关的选项;
·QPrintDialog:        打印机配置;
·QPrintPreviewDialog:打印预览;
·QProgressDialog:        显示操作过程。

代码实现:
//消息对话框
    //关于对话框
    QAction *p1 = pFile->addAction("消息");
    connect(p1,&QAction::triggered,

            [=](){

        QMessageBox::about(this,"abput","关于");
    });

    //问题对话框
    QAction *p2 = pFile->addAction("问题");
    connect(p2,&QAction::triggered,

            [=](){

        int ret = QMessageBox::question(this,"question","are you ok?",QMessageBox::Ok|QMessageBox::Cancel);
        switch(ret){
            case QMessageBox::Ok:
            qDebug() << "i am ok!";
                break;
            case QMessageBox::Cancel:
            qDebug() << "i am bed!";
            break;

           default:
            break;

        }
    });
    //文件对话框
    QAction *p3 = pFile->addAction("文件");
    connect(p3,&QAction::triggered,

            [=](){

        QString path = QFileDialog::getOpenFileName(this,"open","../",

                                               "souce(*.cpp *.h);;Text(*.txt);;all(*.*)"
                                                    );
        qDebug() << path;
    });

5 常用控件
5.1 QLabel 控件
    显示文本,图片和动画等。
(1)显示普通文本、html
    QLable *label = new QLable;
    label->setText(“Hello, World!”);

    label ->setText("<h1><a href=\"https://www.baidu.com\">
百度一下</a></h1>");
    label ->setOpenExternalLinks(true);
            //设置用户点击链接之后是否自动打开链接


(2)显示图片
    QPixmap pixmap;
    pixmap.load(":/Image/boat.jpg");
    QLabel *label = new QLabel;
    label.setPixmap(pixmap);

(3)显示动画
    QMovie *movie = new QMovie(":/Mario.gif");
    movie->start();
    QLabel *label = new QLabel;
    label->setMovie(movie);


5.2 QLineEdit
    Qt提供的单行文本编辑框。


6 布局管理器
    Qt 提供了两种组件定位机制:绝对定位和布局定位。

6.1 水平/垂直/网格布局


 

相关文章

学习编程是顺着互联网的发展潮流,是一件好事。新手如何学习...
IT行业是什么工作做什么?IT行业的工作有:产品策划类、页面...
女生学Java好就业吗?女生适合学Java编程吗?目前有不少女生...
Can’t connect to local MySQL server through socket \'/v...
oracle基本命令 一、登录操作 1.管理员登录 # 管理员登录 ...
一、背景 因为项目中需要通北京网络,所以需要连vpn,但是服...