Qt学习:文件介绍+对象树+信号和槽

Qt.

文章目录

    • Qt.
        • 1.qr的优点
        • 2.成功案例
        • 3.QWidget、QMainWindow和QDialog之间的关系
        • 4.mian.cpp文件
        • 5..pro文件
        • 6..h文件
        • 7.命名规范+快捷键
          • **命名规范**
          • 快捷键
        • 8.对象模型(对象树)
          • 1.浅层
          • 2.深层
        • 9.坐标系
        • 10.信号和槽机制
          • 1.函数
          • 2.按钮常用

1.qr的优点
  • 跨平台
  • 接口简单,易上手
  • 一定程度上简化了内存回收机制
  • 开发效率高(可快速构建应用程序)
  • 发展前景好
  • 可进行嵌入式开发
2.成功案例
  • Linux桌面环境KDE
  • Skype网络电话
  • 谷歌地图
  • VLC多媒体播放器
  • Virtual Box虚拟机软件
  • 咪咕音乐
  • WPS Office
  • 极品飞车
3.QWidget、QMainWindow和QDialog之间的关系

QWidget和QMainWindow是QWidget的子类。

  1. QWidget是所有用户界面元素的基类,窗口和空间都直接或间接继承自QWidget。
  2. QMainWindow是最常见的窗口形式,包括菜单栏、工具栏、状态栏、标题栏等,可作为GUI程序的主窗口。
  3. QDialog是对话框窗口的基类,没有菜单栏、工具栏、状态栏等。(对话框主要用来执行短期任务,或与用户进行交互,可以是模态【打开此窗口不可以操作其他窗口】也可以是非模态【打开此窗口,可以操作其他窗口】)

如果是主窗口,就使用QMainWindow.

如果是对话框,就使用QDialog.

如果不确定,既可能作为顶级窗口,也可能嵌入到其他窗口,则使用QWidget.

注:窗口和控件都继承自QWidget,若不为控件指定父对象,他就会被作为窗口处理,这时setWindowTitle() 【设置窗口标题】和 setWindowIcon() 函数【设置窗口图标】就会生效。

4.mian.cpp文件
#include "mywidget.h"
#include 	//包含一个应用程序类的头文件


//main程序入口	argc命令行变量的数量	argv命令行变量的数组
int main(int argc, char *argv[])
{
    
    QApplication a(argc, argv);		//a应用程序对象,在Qt中,应用对象程序有且仅有一个
    
    myWidget w;			//窗口对象	myWidget父类	-> QWidget
    
    w.show();			//窗口对象默认不会显示,必须调用show方法显示窗口

    return a.exec();	//让程序进入消息循环机制
}

5…pro文件

工程文件(project),qmake自动生成,用于makefile的配置文件

QT       += core gui //Qt包含的模块

greaterThan(QT_MAJOR_VERSION, 4): QT += widgets	//大于4版本  包含widget模块

TARGET = first  //目标    生成.exe程序的名称
TEMPLATE = app	//模板	应用程序模板 Application
/*	
app -建立一个应用程序的makefile。这是默认值,所以如果模板没有被指被使用。
lib - 建立一个库的makefile。
vcapp - 建立一个应用程序的VisualStudio项目文件。
vclib - 建立一个库的VisualStudio项目文件。
subdirs -这是一个特殊的模板,它可以创建一个能够进入特定目录并且为一个项目文件生成makefile并且为它调用make的makefile。
*/

# The following define makes your compiler emit warnings if you use
# any feature of Qt which has been marked as deprecated (the exact warnings
# depend on your compiler). Please consult the documentation of the
# deprecated API in order to know how to port your code away from it.
DEFINES += QT_DEPRECATED_WARNINGS

# You can also make your code fail to compile if you use deprecated APIs.
# In order to do so, uncomment the following line.
# You can also select to disable deprecated APIs only up to a certain version of Qt.
#DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000    # disables all the APIs deprecated before Qt 6.0.0
    
    
/*CONFIG用来告诉qmake关于应用程序的配置信息。*/
CONFIG += c++11  	
/*使用c++11的特性,在这里使用“+=”,是因为我们添加我们的配置选项到任何一个已经存在中。这样做比使用“=”那样替换已经指定的所有选项更安全。*/
    
SOURCES += \			//源文件
        main.cpp \
        mywidget.cpp

HEADERS += \			//头文件
        mywidget.h

# Default rules for deployment.
qnx: target.path = /tmp/$${TARGET}/bin
else: unix:!android: target.path = /opt/$${TARGET}/bin
!isEmpty(target.path): INSTALLS += target

6…h文件
#ifndef MYWIDGET_H
#define MYWIDGET_H

#include 	//包含头文件QWidget 窗口类

class myWidget : public QWidget
{
    Q_OBJECT宏,允许类中使用信号和槽的机制	// Q_OBJECT宏,允许类中使用信号和槽的机制

public:
    myWidget(QWidget *parent = 0);	//构造函数
    ~myWidget();	//析构函数
};

#endif // MYWIDGET_H

7.命名规范+快捷键
命名规范
  • 类名首字母大写,单词和单词之间首字母大写
  • 函数名变量名称首字母小写,单词和单词之间首字母大写
快捷键
  • 注释 ctrl +/

  • 运行 ctrl + r

  • 编译 ctrl + b

  • 字体缩放 ctrl +鼠标滚轮

  • 查找 ctrl + f

  • 整行移动 ctrl +shift +↑或者↓

  • 帮助文档 F1 或 文件目录(我的:E:\qt\5.12.0\mingw73_64\bin)

  • 自动对齐 ctrl+i

  • 同名.h和.cpp文件切换 F4

8.对象模型(对象树)
1.浅层

在Qt中创建对象的时候会提供一个Parent对象指针

  • QObject是以对象树的形式组织起来的。

    • n 当你创建一个QObject对象时,会看到QObject的构造函数接收一个QObject指针作为参数,这个参数就是 parent,也就是父对象指针。

      这相当于,在创建QObject对象时,可以提供一个其父对象,我们创建的这个QObject对象会自动添加到其父对象的children()列表。

    • n 当父对象析构的时候,这个列表中的所有对象也会被析构。(注意,这里的父对象并不是继承意义上的父类!)

  • 当创建的对象在堆区时,如果指定的父亲是QObject派生下来的类或QObject子类派生下来的类,可以不用管理释放的操作,将对象放回到对象树中。

  • 一定程度上简化了内存回收机制

Qt学习:文件介绍+对象树+信号和槽_第1张图片

2.深层

在Qt中创建对象的时候会提供一个Parent对象指针,下面来解释这个parent到底是干什么的。

  • lQObject是以对象树的形式组织起来的。

    • 当你创建一个QObject对象时,会看到QObject的构造函数接收一个QObject指针作为参数,这个参数就是 parent,也就是父对象指针。这相当于,在创建QObject对象时,可以提供一个其父对象,我们创建的这个QObject对象会自动添加到其父对象的children()列表。

    • n 当父对象析构的时候,这个列表中的所有对象也会被析构。(注意,这里的父对象并不是继承意义上的父类!)

  • QWidget是能够在屏幕上显示的一切组件的父类。

    • QWidget继承自QObject,因此也继承了这种对象树关系。一个孩子自动地成为父组件的一个子组件。因此,它会显示在父组件的坐标系统中,被父组件的边界剪裁。例如,当用户关闭一个对话框的时候,应用程序将其删除,那么,我们希望属于这个对话框的按钮、图标等应该一起被删除。事实就是如此,因为这些都是对话框的子组件。

    • 当然,**我们也可以自己删除子对象,它们会自动从其父对象列表中删除。**比如,当我们删除了一个工具栏时,其所在的主窗口会自动将该工具栏从其子对象列表中删除,并且自动调整屏幕显示。

Qt学习:文件介绍+对象树+信号和槽_第2张图片

Qt 引入对象树的概念,在一定程度上解决了内存问题。

  • 当一个QObject对象在堆上创建的时候,Qt 会同时为其创建一个对象树。不过,对象树中对象的顺序是没有定义的。这意味着,销毁这些对象的顺序也是未定义的。

  • l 任何对象树中的 QObject对象 delete 的时候,如果这个对象有 parent,则自动将其从 parent 的children()列表中删除;如果有孩子,则自动 delete 每一个孩子。Qt 保证没有QObject会被 delete 两次,这是由析构顺序决定的。

如果QObject在栈上创建,Qt 保持同样的行为。正常情况下,这也不会发生什么问题。

来看下下面的代码片段:

{

  QWidget window;

  QPushButton button = QPushButton ("退出", &window);

}

作为父组件的 window 和作为子组件的 quit 都是QObject的子类(事实上,它们都是QWidget的子类,而QWidget是QObject的子类)。这段代码是正确的,quit 的析构函数不会被调用两次,因为标准 C++要求,局部对象的析构顺序应该按照其创建顺序的相反过程。因此,这段代码在超出作用域时,会先调用 quit 的析构函数,将其从父对象 window 的子对象列表中删除,然后才会再调用 window 的析构函数。

但是,如果我们使用下面的代码:

{

  QPushButton quit("Quit");

  QWidget window;

  quit.setParent(&window);

}

情况又有所不同,析构顺序就有了问题。我们看到,在上面的代码中,作为父对象的 window 会首先被析构,因为它是最后一个创建的对象。在析构过程中,它会调用子对象列表中每一个对象的析构函数,也就是说, quit 此时就被析构了。然后,代码继续执行,在 window 析构之后,quit 也会被析构,因为 quit 也是一个局部变量,在超出作用域的时候当然也需要析构。但是,这时候已经是第二次调用 quit 的析构函数了,C++ 不允许调用两次析构函数,因此,程序崩溃了。

由此我们看到,Qt 的对象树机制虽然帮助我们在一定程度上解决了内存问题,但是也引入了一些值得注意的事情。这些细节在今后的开发过程中很可能时不时跳出来烦扰一下,所以,我们最好从开始就养成良好习惯。

在 Qt 中,尽量在构造的时候就指定 parent 对象,并且大胆在堆上创建。

Qt学习:文件介绍+对象树+信号和槽_第3张图片

9.坐标系

左上角为原点,X向右增加,Y向下增加

被嵌套窗口先对于父窗口来说
Qt学习:文件介绍+对象树+信号和槽_第4张图片

10.信号和槽机制
1.函数

connect()函数最常用的一般形式:

connect(sender, signal, receiver, slot);

参数解释:

  • sender:发出信号的对象

  • signal:发送对象发出的信号

  • receiver:接收信号的对象

  • slot:接收对象在接收到信号之后所需要调用的函数(槽函数)

Qt学习:文件介绍+对象树+信号和槽_第5张图片

2.按钮常用
  • void clicked(bool checked = false) 点击事件
  • void pressed () 按下事件
  • void released() 松开事件
  • void toggled(bool checked) 切换事件

你可能感兴趣的:(Qt,qt,学习,开发语言)