1.main函数介绍

//main函数为程序的入口,argc为命令行变量的数量,argv为命令行变量的数组
int main(int argc, char* argv[])
{
    //定义QApplication对象,一个Qt应用程序有且仅有一个应用程序对象.
    QApplication a;
    //应用程序对象进入消息循环机制
    return a.exec();
}

2.QT中常用快捷键

  1. 运行:ctrl + r;
  2. 编译:ctrl + b;
  3. 查找:ctrl + f;
  4. 帮助文档:第一种方法光标移到类名再按下F1;第二种将Qt安装包下的assistant.exe路径配置到系统环境变量中。
  5. F4进行同名之间的文件快速切换。比如说xxx.h到xxx.cpp就可以按下F4.
  6. 字体缩放:ctrl + 鼠标滚轮。
  7. 注释:ctrl + /
  8. 自动补齐格式:CTRL+i
  9. 将某行代码上移或者下移:CTRL +shift+PgUp/Ctrl+shift+PgDn

3.Qt中向控制台输出信息

#include <QDebug>
qDebug() << "Qt向控制台输出信息";  //qDebug会自动换行

4.Qt中的信号和槽

connect函数:

  1. 参数一:信号发送者
  2. 参数二:发送的信号(信号地址)
  3. 参数三:信号接收者
  4. 参数四:处理信号的槽函数(槽函数地址)
    对于参数二和参数四:如果出现自定义信号和自定义槽函数重载时,传递信号的地址或者槽函数的地址作为实参是摸棱两可的。所以需要传递函数指针作为实参。

例如:connect(myButton,&QPushButton::clicked,this,&MyWidget::close)
Qt4版本以前的信号和槽的连接方式:
connect(myButton,SIGNAL(clicked()),this,SLOT(close()))

disconnect函数: 断开信号的连接

自定义类中自定义信号和槽

class Example:public QObject
{
//QT中的自定义信号必须声明在signals下面
//1.信号没有返回值,返回值类型为void
//2.信号可以有参数,可以重载
//3.信号只需要声明而不用实现。
    signals:
        void mySignal();

//QT中的自定义槽函数声明在public slots下面,但是在高版本中可以声明在全局区或者Public访问权限符下
//1.槽函数需要声明,必须定义
//2.槽函可以有参数,可以重载
//3.槽函数返回值类型为void
    public slots:
        void myslot(); 
}

emit:触发自定义信号的关键字。语法:

emit Example类对象->自定义信号名();

信号和槽的扩展:

  1. 信号是可以连接信号的
  2. 信号和槽可以通过disconnect函数断开的
  3. 一个信号可以连接多个槽函数
  4. 多个信号可以连接同一个槽函数
  5. 信号和槽函数的个数必须一一对应。(信号的个数可以大于槽函数的个数反之不可以)

Lambda表达式:
C++11的Lambda表达式用于定义并创建匿名的函数对象。Lambda表达式的基本构成:

[capture](parameters)mutable->return-type
{
    statement
}
//[函数对象参数](操作符重载函数参数)mutable->返回值
//{
        函数体  
//}
函数对象参数有以下几种形式:
1.空:没有使用任何函数对象参数
2.=:函数体内可以使用Lambda所在作用范围内所有可见的局部变量。值传递方式
3.&:引用传递方式
4.this:函数体内可以使用Lambda所在类中的成员变量
5.a:将a按照值传递。按照值进行传递时,函数体内不能修改传递进来的a的拷贝,因为默认情况是const的.要修改传递进来的a的拷贝(不能修改值a本身),可以添加mutable修饰符。
6.&a:将a按照引用传递

使用示例:

    int number = 100;
    //因为mutable修饰符,在Lambda表达式函数体内可以修改number这个值的拷贝,但是不影响number值本身
    connect(button,&QPushButton::clicked,this,[=]()mutable{number += 100;qDebug() << number;}); //200
    qDebug() << number; //100

    int ret = []()->int{return 1000;}();
    qDebug() << ret;    //1000

    //利用Lambda表达式实现点击按钮关闭窗口
    QPushButton * button = new QPushButton("关闭窗口",this);
    connect(button,&QPushButton::clicked,this,[=](){
        this->close();
    });

5.菜单栏

如下图所示是一个window记事本中的一个菜单栏

image.png

如下图所示是菜单项

image.png

则代码片段示例如下:
在mainWindow.cpp中

#include "mainwindow.h"
#include <QMenuBar>
#include <QAction>

MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
{
    this->setWindowTitle("记事本");
    this->resize(600,600);
    //创建菜单栏
    QMenuBar* bar = new QMenuBar(this);
    //将菜单栏添加到主窗口中
    this->setMenuBar(bar);

    //给菜单栏添加菜单
    QMenu* menu1 = bar->addMenu("文件(F)");
    QMenu* menu2 = bar->addMenu("编辑(E)");
    QMenu* menu3 = bar->addMenu("格式(O)");
    QMenu* menu4 = bar->addMenu("查看(V)");
    QMenu* menu5 = bar->addMenu("帮助(H)");

    //给菜单添加菜单项
    menu1->addAction("新建(N)     CTRL+N");
    //添加分割副
    menu1->addSeparator();
    menu1->addAction("打开(O)     CTRL+O");
    
    //注:上述代码还未添加热键
}

MainWindow::~MainWindow()
{
}

运行结果如下:
image.png

6.工具栏

QToolBar * tool = new QToolBar(this);
//将工具栏添加进主窗口中
this->addToolBar(tool);
//设置工具栏停靠位置在左边
tool->setAllowedAreas(Qt::LeftToolBar);
//设置工具栏不可浮动
tool->setFloatable(false);
//固定住工具栏
tool->setMoveable(false);

//给工具栏添加菜单项
tool->addAction(action1);
//添加分隔符
tool->addSeparator();
//给工具栏添加菜单项
tool->addAction(action2);

7.状态栏

//一个主窗口中状态栏只能有一个
QStatusBar * bar = new QStusBar();
//将状态栏添加进主窗口中
this->setStatusBar(bar);
//状态栏中添加标签
QLabel* label = new QLabel("提示信息",this);
bar->addWidget(label);

8.铆接部件(浮动窗口可以有多个)

//创建铆接部件对象
QDockWidget* widget = new QDockWidge(this);
//将铆接部件添加进主窗口中
addDockWidget(Qt::DockWidgetArea area, QDockWidget *dockwidget);
//设置停靠范围(浮动窗口的停靠位置相对于中心部件而言的)
setallowedAreas(Qt::DockWidgetAreas areas);

9.核心部件(中心部件只能有一个)

QTextEdit* edit = new QTextEdit(this);
//将核心部件添加进主窗口中
setCentralWidget(QWidget *widget);

10.给Qt项目添加资源文件

  1. 将需要添加的资源放置项目下.
  2. 选中项目右击add new,然后添加Qt的Qt resource file.
  3. 右击新建的后缀名为.qrc的资源文件,然后open in editor。
  4. 先设置前缀,然后将你需要添加的资源文件(比如说图标)添加进来。
  5. 资源文件的使用:”:+你设置的前缀+文件名“

举例:给主窗口标题设置图标

MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
{
    //添加菜单栏
    QMenuBar* mbar = new QMenuBar();
    this->setMenuBar(mbar);

    //添加菜单
    QMenu* menu1 = mbar->addMenu("文件(F)");
    QMenu* menu2 = mbar->addMenu("编辑(E)");
    QMenu* menu3 = mbar->addMenu("格式(O)");
    QMenu* menu4 = mbar->addMenu("查看(V)");
    QMenu* menu5 = mbar->addMenu("帮助(H)");

    //添加菜单项
    menu1->addAction("新建(N)    CTRL+N");
    menu1->addAction("打开(O)...    CTRL+O");
    menu1->addAction("保存(S)...    CTRL+S");

    //添加文本编辑区(核心部件)
    QTextEdit* edit = new QTextEdit();
    this->setCentralWidget(edit);

    //调整主窗口大小
    this->resize(600,600);
    //设置图标
    this->setWindowIcon(QIcon(":/img/timg.jpg"));
    //设置主窗口标题
    this->setWindowTitle("无标题 -记事本");

}

运行如下:
image.png
当然了,你可以通过ui设置图标。

10.对话框

1.对话框的分类:

  1. 模态对话框:弹出一个对话框如果不对当前对话框进行相应的操作,是不能进行其他的操作的。
  2. 非模态对话框:弹出一个对话框如果不对当前对话框进行相应的操作,也可以进行其他的操作的。

示例创建一个模态对话框和一个非模态对话框:

//    //当点击打开这个菜单项打开时,创建一个模态对话框
//    connect(action2,&QAction::triggered,this,[=]()

//    {
//        //创建一个模态对话框
//        QDialog dialog(this);
//        dialog.resize(100,100);
            //exec()函数有阻塞功能
//        dialog.exec();
            //当关闭模态对话框后才会打印Hello
//        qDebug() << "Hello";
//    });

    connect(action2,&QAction::triggered,this,[=]
    {
        //创建非模态对话框时我们不使用栈上的对象,而使用堆上的对象
        QDialog* dialog = new QDialog(this);
        dialog->resize(100,100);
        dialog->show();
        //设置属性,是为了当关闭非模态对话框时立即释放堆上的资源。
        dialog->setAttribute(Qt::WA_DeleteOnClose);

        qDebug() << "Hello";
    });

当然了通过ui文件也是可以创建模态对话框和非模态对话框的。

2.标准对话框。
Qt内置了一些标准对话框。

标准对话框QMessageBox(消息对话框)的使用:

//当点击“打开“这个菜单项弹出消息对话框
    connect(action2,&QAction::triggered,this,[=]()
    {
        //错误对话框X
        //QMessageBox::critical(this,"错误","error");
        //信息对话框i
        //QMessageBox::information(this,"OK","退出");
        QMessageBox::information(this,"记事本","是否将更改保存到xxx.txt",QMessageBox::Save,
                                 QMessageBox::No,
                                 QMessageBox::Cancel);
        //问题对话框?
        //警告对话框!
    });

3.颜色对话框QColorDialog的使用:

//创建颜色对话框
    connect(action2,&QAction::triggered,this,[=]{
        QColor color = QColorDialog::getColor(QColor(255,0,0));
        //获取颜色对话框中的三种颜色值
        qDebug() << color.red() << color.green() << color.blue();
    });

4.标准文件对话框的使用

 //创建文件对话框
    connect(action2,&QAction::triggered,this,[=]
    {
        //参数四为过滤路径,返回值为选择的文件的路径
        QString fileName = QFileDialog::getOpenFileName(this,
              tr("打开"), "C:\\Users\\lenovo\\Desktop", tr("Image Files (*.png *.jpg *.bmp)"));
        qDebug() << fileName;
    });

5.选择字体对话框(QFontDialog)

//字体对话框
    bool ok;
    QFont font = QFontDialog::getFont(&ok, QFont("Times New Roman", 12), this,"字体对话框");
    // font is set to the font the user selected
    if (ok)
    {
      //获取用户选择的字体信息
      qDebug() << "字体:" << font.family() << "字号:" << font.pointSize() <<
                  "是否加粗:" << font.bold() << "是否倾斜:" << font.italic();

    // the user canceled the dialog; font is set to the initial
    // value, in this case Times, 12.
    }
    else
    {
      qDebug() << font.family() << font.pointSize();
    }

6.输入对话框(QInputDialog) 等等...

11.ui模拟实现一个登录窗口

12.常用控件按钮

  1. ToolButton一般用于显示图片用,PushButton一般不用于显示图片。
  2. GroupBox这个容器用于分组,一般和单选按钮RadioButton或者CheckBox复选按钮结合使用
    image.png

13常用的item Widgets使用

1.List Widget控件的使用
//使用listWidget写一首小诗
    //方法一
    QListWidgetItem* item1 = new QListWidgetItem("静月思");
    item1->setTextAlignment(Qt::AlignHCenter);   //设置文本对齐方式为居中
    ui->listWidget->addItem(item1);

    QListWidgetItem* item2 = new QListWidgetItem("床前明月光,疑是地上霜");
    item2->setTextAlignment(Qt::AlignHCenter);   //设置文本对其
    ui->listWidget->addItem(item2);

    //方法二
    //或者呢通过QStringList类,但是这种方式无法设置文本对齐方式
    QStringList list;
    list << "举杯望明月,低头思故乡";
    ui->listWidget->addItems(list);

image.png

2.Tree Widget控件的使用
  1. 先设置头setHeaderLabels方法
  2. 添加顶层项目addTopLevelItem方法
  3. 添加子项目addChild方法
    ui->setupUi(this);
    //县设置头
    ui->treeWidget->setHeaderLabels(QStringList() << "家庭成员" << "成员介绍");
    //添加顶层项目
    QTreeWidgetItem* item1 = new QTreeWidgetItem(QStringList() << "伯伯");
    ui->treeWidget->addTopLevelItem(item1);

    QTreeWidgetItem* item2 = new QTreeWidgetItem(QStringList() << "自己");
    ui->treeWidget->addTopLevelItem(item2);

    //添加子项目
    QTreeWidgetItem* chItem1 = new QTreeWidgetItem(QStringList() << "儿子" << "崇明");
    item1->addChild(chItem1);
    QTreeWidgetItem* chItem2 = new QTreeWidgetItem(QStringList() << "女儿" << "傻子");
    item1->addChild(chItem2);

    QTreeWidgetItem* chItem3 = new QTreeWidgetItem(QStringList() << "儿子" << "崇明");
    item2->addChild(chItem3);
    QTreeWidgetItem* chItem4 = new QTreeWidgetItem(QStringList() << "女儿" << "傻子");
    item2->addChild(chItem4);

运行结果如下:
image.png

3.Table Widget控件的使用
  1. 先设置表的列数通过setColumnCount方法
  2. 添加水平头通过setHorizontalHeaderLabel方法
  3. 设置行数setRowCount方法
  4. 设置正文(行数,列数,具体内容)
//TableWidget控件创建一个表格

    //1.设置表的列数
    ui->tableWidget->setColumnCount(3);
    //2.设置水平表头
    ui->tableWidget->setHorizontalHeaderLabels(QStringList() << "姓名" << "性别" << "年龄");
    //3.设置行数
    ui->tableWidget->setRowCount(3);
    //4.设置正文
    QStringList nameList;
    nameList << "张三" << "李四" << "王五";

    QList<QString>sexList;
    sexList << "男" << "男" << "女";
    for(int i = 0; i < 3; i++)
    {
        int column = 0;
        ui->tableWidget->setItem(i,column++,new QTableWidgetItem(nameList[i]));
        ui->tableWidget->setItem(i,column++,new QTableWidgetItem(sexList.at(i)));
        //int转成QString 
        ui->tableWidget->setItem(i,column,new QTableWidgetItem(QString::number(i + 18)));
    }

image.png

4.其他常用控件
  1. Scroll Area:滚动条的区域

image.png
2. Tool Box:分页

image.png
3. tab Widget:
image.png
4. Stacked Widget:
5. combo box:下拉框

image.png
6. line edit:单行编辑框,输入账号密码信息可以使用这个控件

注意:
1. 对于设置密码的显示模式,可以使用QLineEdit的setEchoMode方法。

2. 设置QLineEdit单行编辑框的输入提示,可以使用setCompleter方法。
比如说:

QStringList list;
list << "haha" << "hello" << "How are you";

QCompleter* completer = new QCompleter(list,this);
//设置匹配时不区分大小写
completer->setCaseSensitivity(Qt::CaseInsensitive);

//设置字符串部分匹配可以使用QCompleter类中的setFilterMode方法
completer->setFilterMode(Qt::MatchContains);

QLineEdit* line = new QLineEdit(this);
line->setCompleter(completer);

实现效果如图:
image.png

  1. span box

image.png

  1. Label:可以显示图片
//利用Lable显示图片
    ui->label->setPixmap(QPixmap(":/img/t01de95bed9f4ebdc07.webp"));

运行结果如下:

image.png

利用Label还可以显示GIF动图

    //Label显示GIF动图
    QMovie* movie = new QMovie(":/image/1306351.gif");
    ui->label->setMovie(movie);
    //播放GIF
    movie->start();
    //让GIF动画自适应Label大小
    ui->label->setScaledContents(true);

利用Label还可以显示互联网上的有效链接

    //设置HTML语句
    ui->label->setText("<h1><a href = \"https://www.baidu.com\">百度</a></h1>");
    //setOpenEternalLinks()设置用户点击链接后自动打开。
    ui->label->setOpenExternalLinks(true);
    //让链接自适应Label大小
    ui->label->setScaledContents(true);
5.自定义控件的封装:涉及到Qt设计师界面类的自定义创建和类的提升(使用自定义的控件)等

14.常用事件

QEvent类是所有事件类的基类

  1. 鼠标进入事件:enterEvent
  2. 鼠标离开事件:leaveEvent
  3. 鼠标按下,鼠标移动,鼠标释放:
mousePressEvent
mouseMoveEvent
mouseReleaseEvent

如果需要捕获鼠标按下或者移动或者释放的事件,需要重写event handler(就是对一些事件处理函数即虚函数重写)。比如说:用于鼠标按下的事件处理函数。

void MyLabel::mousePressEvent(QMouseEvent *event)
{
    int x = event->x();
    int y = event->y();

    //<center>和<h1>均为HTML中的标签,分别表示文字居中和一级标题
    QString text = QString("<center><h1>mouse press:(%1,%2)</h1></center>") .arg(x).arg(y);
    this->setText(text);
}

获取鼠标释放时的坐标:

void MyLabel:: mouseReleaseEvent(QMouseEvent *event)
{
    QString text = QString("<center><h1>mouse release:(%1,%2)</h1></center>") .arg(event->x()).arg(event->y());
    this->setText(text);
}

image.png
4. 事件接受与忽略。accept函数与ignore函数
事件的接受与忽略一般用于closeEvent事件处理函数中。closeEvent事件处理函数的默认行为是接受形参event这个事件并且关闭窗口。应用示例如下:

void Widget::closeEvent(QCloseEvent* ev)
{
    int ret = QMessageBox::question(this,"question","are you assure quit?");
    if(ret == QMessageBox::Yes)
    {
        ev->accept();
    }
    else
    {
        ev->ignore();
    }
}

运行如下:
image.png

  1. 定时器事件:

1.设置定时器方法1:
starttimer启动计时器,TimeEvent中的timerId()用于区分计时器。

2.设置定时器方法2:

    //需要在ui文件中先拖动一个label.
    ui->setupUi(this);
    //设置计时器
    QTimer* time = new QTimer(this);
    //1000毫秒后启动计时器
    time->start(1000);
    connect(time,&QTimer::timeout,this,[=](){
        static int num = 0;
        ui->label->setText(QString::number(num++));
    });

运行结果如下:
image.png

3.利用QTimer实现一个定时器:

//前提在ui文件中拖动一个label
ui->setupUi(this);
    //设置计时器
    QTimer* time = new QTimer(this);
    //启动计时器
    time->start(1000);
    connect(time,&QTimer::timeout,this,[=](){
        static int num = 0;
        ui->label->setText(QString::number(num++));
    });
    connect(ui->pushButton,&QPushButton::clicked,this,[=](){
        time->stop();
    });

运行结果如下:

image.png

实现一个简易的定时器1:

 ui->setupUi(this);
    this->setWindowTitle("定时器");
    this->setWindowIcon(QIcon(":/icon/Desert.jpg"));
    this->setFixedSize(400,200);

    //创建定时器对象
    QTimer* time = new QTimer(this);
    //每一秒钟加一
    time->start(1000);
    connect(time,&QTimer::timeout,this,[=](){
            static int num = 0;
            ui->label->setText(QString::number(num++));
        });
    connect(ui->pushButton,&QPushButton::clicked,this,[=](){
        time->stop();
    });

运行结果如下:
image.png

4.实现一个简易的定时器2:在类中重写timerEvent方法

void Widget::timerEvent(QTimerEvent *e)
{
    static int num = 0;
    ui->label->setText(QString("<center><h1>time out:%1</h1></center>").arg(num++));
}

然后启动计时器:

//timeId为定时器的唯一标识
int timeId = this->startTimer(1000);

5. event事件

主要功能进行事件的分发.event函数并不直接对事件进行处理,而是按照事件对象的类型分派给特定的事件处理函数。可以重写此函数定制此函数的行为。
函数:bool event(QEvent *);
返回值为true表示用户自己处理,不向下分发事件,时间停止传播下去。
返回值为false代表系统处理,但是最好抛给父类处理。

bool MyWidget::event(QEvent * e)
{
    //如果是鼠标按下,在event事件分发中做拦截操作
    if(e->type() == QEvent::MouseButtonPress)
    {
        
    }
    //其他事件交给父类处理,默认处理
    return QWidget::event(e);
}

6. 事件过滤器
image.png

在特定对象上安装事件过滤器,该过滤器仅过滤该对象收到的事件。然后再类中重写事件过滤函数。

步骤如下:
1.安装过滤器
ui->label->installEventFilter(this);
2.重写eventFiter事件过滤函数

class MainWindow : public QMainWindow
  {
  public:
      MainWindow();

  protected:
      bool eventFilter(QObject *obj, QEvent *ev) override;

  private:
      QTextEdit *textEdit;
  };

  MainWindow::MainWindow()
  {
      textEdit = new QTextEdit;
      setCentralWidget(textEdit);

      textEdit->installEventFilter(this);  //给textEdit这个控件安装事件过滤器
  }

  bool MainWindow::eventFilter(QObject *obj, QEvent *event)
  {
//仅过滤textEdit这个对象收到的事件
      if (obj == textEdit)
      {
          if (event->type() == QEvent::KeyPress)
          {
              QKeyEvent *keyEvent = static_cast<QKeyEvent*>(event);
              qDebug() << "Ate key press" << keyEvent->key();
              return true;
          } 
          else
          {
              return false;
          }
      } 
      else
      {
          // pass the event on to the parent class
          return QMainWindow::eventFilter(obj, event);
      }
  }

15QPainter实现基本绘图

0.QT的绘画系统组要基于这三个类: QPainter, QPaintDevice, and QPaintEngine

1.画家使用画笔:

void Widget::paintEvent(QPaintEvent* event)
{
    //创建画家对象,初始化一个painter对象
    //this指定绘图设备
    QPainter painter(this);
    //创建画笔 
    QPen pen(QColor(255,0,0));
    //画家拿起笔
    painter.setPen(pen);
    //利用画家画直线
    painter.drawLine(QPoint(0,0),QPoint(100,100));
}

运行结果如下:
image.png
2.画家使用画刷

    //创建画刷
    QBrush brush(Qt::black);
    //画家使用画刷
    painter.setBrush(brush);

    //利用画家画圆
    painter.drawEllipse(QPoint(50,50),30,30);

运行结果如下:
image.png

3.使用画家画图:
1.

painter.drawPixmap(10,10,QPixmap(":/img/Koala.jpg"));
  1. 画一个背景图
void Widget::paintEvent(QPaintEvent *event)
{
    QPainter* painter = new QPainter(this);
    painter->drawPixmap(0,0,this->width(),this->height(),QPixmap("C:\\Users\\zhihua\\Pictures\\example.jpg"));
}

16.QFile文件读写

  1. 首先页面布局:
    image.png

对于上图的大致布局步骤如下:

  1. 选择widget容器
  2. 拖动line edit(单行输入框)和一个push_button到容器内,然后选择水平布局
  3. 拖动一个text edit到布局界面内
  4. 对整体进行垂直布局即可。
    现在欲实现一个类似于windows记事本打开的功能
MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
        ui->setupUi(this);
        //当点击选择路径时,就弹出一个文件对话框
        connect(ui->pushButton,&QPushButton::clicked,this,[=](){
        QString name = QFileDialog::getOpenFileName(this,"打开文件","C:\\Users\\zhihua\\Desktop",tr("Text files (*.txt);;Images (*.png *.xpm *.jpg)"));
        if(name.isEmpty())
        {
            QMessageBox::warning(this,"警告","打开文件失败");
        }
        //将路径放到line edit中
        ui->lineEdit->setText(name);
        //读取文件内容,QT默认支持UTF—8文件
        QFile file(name);
        file.open(QIODevice::ReadOnly);
        QByteArray array = file.readAll();
        //将读取到的内容放入text edit中
        ui->textEdit->append(array);
        file.close();
    });
}

运行结果如下:
image.png
上诉程序只支持UTF编码格式,并不支持GBK格式:
如果需要支持GBK格式,需要使用QTextCodec类进行选择指定编码格式的类。

    ui->setupUi(this);
    //当点击选择路径时,就弹出一个文件对话框
    connect(ui->pushButton,&QPushButton::clicked,this,[=](){
        QString name = QFileDialog::getOpenFileName(this,"打开文件","C:\\Users\\zhihua\\Desktop",tr("Text files (*.txt);;Images (*.png *.xpm *.jpg)"));
        if(name.isEmpty())
        {
            QMessageBox::warning(this,"警告","打开文件失败");
        }
        //将路径放到line edit中
        ui->lineEdit->setText(name);
        //设置打开编码格式的文件
        QTextCodec* code = QTextCodec::codecForName("gbk");

        //读取文件内容,QT默认支持UTF—8文件
        QFile file(name);
        file.open(QIODevice::ReadOnly);
        QByteArray array = file.readAll();
        //将读取到的内容放入text edit中
        //ui->textEdit->append(array);
        //将字节array转成GBK
        ui->textEdit->setText(code->toUnicode(array));
        file.close();
    });

17.QFileInfo类读取文件信息

18.使用文本流和数据流读写文件(主要涉及到两个类:QTextStream,QDataStream)

19.布局管理器布局

  1. 对于控件比如说QLabel和QLineEdit的布局,可以将它们放在QWidget容器中进行布局,这样就可以按照模块对控件进行布局。

image.png
2. 可以在布局对象属性中更改距离比如说左边距,上边距,右边距,下边距,间隙等。
image.png

20.对象树

当创建的对象在堆区时候,如果指定的父亲是QObject派生下来的类或者QObject子类派生下来的类,可以不用管理释放的操作,将对象会放入到对象树中,一定程度简化了内存回收机制。