Qt学习

帮助手册是最全的编程指导,重点关注

        Properties 、Public Functions、 Signal Protected、 Functions、

注意事项:

  1. 项目名称不能有中文、不能有空格。
  2. 项目路径不能含有中文路径。
  3. 创建文件的三个选项Qwidget,QMainWindow,Qdialog,其中Qwidget是最基本的基类,有一个基本的图形QMainWindow,Qdialog是其的派生类,在Qwidget基础上有所增加。

常用快捷键:

  1. 注释  ctrl + /
  2. 运行  ctrl + r
  3. 编译  ctrl + b
  4. 字体缩放  ctrl + 鼠标左键
  5. 查找  ctrl + f
  6. 整行移动  ctrl + shift + 上或下
  7. 帮助文档  F1
  8. 自动对齐  ctrl + i
  9. 同名之间的.h 和 .cpp的切换  F4

按钮控件常用API:

  1. 创建按钮:QPushButton *btn = new QPushButton
  2. 设置父类:setParent(this)
  3. 设置文本:setText("文本")
  4. 设置位置:move(宽,高)
  5. 重新制定窗口大小:resize(宽,高)
  6. 设置窗口标题:setWinowTitle(“文本”)
  7. 设置窗口固定大小:setFixedSize(宽,高)

Qt的核心内容:界面怎么写,怎么去处理用户的点击或其他事件。

最基本的的Qt程序:只需要两行代码,一个QT程序已经完成,只是没有任何窗口显示。

#include "mainwindow.h"
#include //应用程序类头文件

int main(int argc, char *argv[])
{
//实例化一个QApplication对象
    QApplication a(argc, argv);
//窗口对象  MainWindow的父类->Qwidget
    MainWindow w;
//窗口对象默认不会显示,必须要调用show()方法来显示窗口。
    w.show();
//让应用程序代码在此行循环,阻塞到这一行。
    return a.exec();
}

return a.exec()称为主运行循环

任意一个有界面的程序,它要去进行反应,

它的动力来源于哪里

来源于点击

点击/按键实际是一个事件

怎样去找锁定点击事件,找到用户动作触发的事件。不停的去监听,怎么去监听?

就是通过return a.exec(),所以每次程序执行完,不能让main函数结束,而是通过a.exec()不停监听触发了哪些事件。

#include
#include//Qt提供的一个标签类
int main(int agrc ,char *argv[])
{
	//实例化一个QApplication对象,只需要两行代码一个QT程序已经完成,只是没有任何窗口显示。
	QApplication a(argc,argv);
	QLabel * label = new QLabel("Hello world!");//创建一个标签构造函数
	label->show();//调用标签类中的show函数显示出来。
	return a.exec();
}

linux中自己编写Qt程序:

  1. 首先编写好一个自己的CPP文件。
  2. 使用qmake -project命令进行编译。
  3. 此时会多出来一个.pro文件。
  4. .pro文件记录本程序的一些基本信息,(Qt会根据.pro文件自动的生产平台对应的Makefile文件)。
  5. 再次在命令行中使用qmake(不带任何参数)。
  6. 再次多出一个Makefile文件。
  7. 命令行执行make,会根据Makefile生成可执行程序.o文件。
QT       += core gui //包含的Qt组件信息,核心、图形、窗口

greaterThan(QT_MAJOR_VERSION, 4): QT += widgets //大于4会自动包含widgets模块,提高程序兼容性

TARGET = test  //文件/工程名
TEMPLATE = app  //模板使用哪个


SOURCES += main.cpp\     //源程序使用哪些
        mainwindow.cpp

HEADERS  += mainwindow.h  //头文件使用哪些

FORMS    += mainwindow.ui  //格式使用哪些

mainwindow.h

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include 

namespace Ui {
class MainWindow;
}
//自己声明的MainWindow类继承自Qmainwindow类
//QMainWindow 中定义了一些基本窗口处理,可以在自己继承的类中对其修改,覆盖,重载等。
class MainWindow : public QMainWindow 
{
    Q_OBJECT//Q_OBJECT是一个宏,允许使用信号和槽。

public:
    explicit MainWindow(QWidget *parent = 0);
    ~MainWindow();

private:
    Ui::MainWindow *ui;
};

#endif // MAINWINDOW_H

在一个项目中,如果将功能和外观混在一起放在main函数中,程序将变的非常庞大且混乱,后期维护将十分困难,为了避免这种情况的出现,需要将功能和界面分开。也就是MVC设计模式,模型model、视图view、控制器controller。

controller也就是:mainwindow.cpp和mainwindow.h。

view是:mainwindow.ui。

任何屏幕上所见的控件都是继承自Qwidget。

绝大部分的类的父类都是QObject类,包括主窗口的MainWindow。

QObject类只有一个成员objectname,每一个对象都必须有名字,而且名字是唯一的。

对象树:

  1. 当创建的对象在堆区的时候,如果指定的父亲是QObject派生下来的类或者是QObject子类派生下来的类,完全不用管理对象的释放,系统会将对象放在对象树中统一管理。
  2. 一定程度上简化了内存回收。

Qt学习_第1张图片

信号与槽

在哪里写?mainwindow类中。

怎么写?哪个元素?哪种操作?

搭建界面->添加功能->链接信号与槽。

信号与槽的关键函数connect(谁,触发了什么信号,谁,执行什么操作)。

第一种方法,自己手动编写链接和断开连接函数。

当自己手动编写程序时,怎么确定label的属性更改应该写什么函数?

通过查看帮助手册确定:属性的设置基本分为三种情况:

  1. 返回类型是非BOOL类型,那么设置函数一定是set+属性的英文单词,例如设置文本settext(),获取文本则是text()。
  2. 返回类型是BOOL类型,设置函数一定是set+属性的英文单词,例如设置执行setExclusive(),获取设置则是exclusive()。
  3. 返回类型是BOOL类型,设置函数一定是set+属性的英文单词,获取函数是is+属性的英文单词。

mainwindow.h

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include 

namespace Ui {
class MainWindow;
}

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = 0);
    ~MainWindow();
/************************************************************/
//槽函数的声明方法
private slots:
    void cclogin();
    void cc_close();
/************************************************************/
private:
    Ui::MainWindow *ui;
};

#endif // MAINWINDOW_H

mainwindow.cpp

#include "mainwindow.h"
#include "ui_mainwindow.h"
/**********************************************************************/
#include//控制台输出需要包含
#include//Qt中字符串处理类,类似C++的string类
/**********************************************************************/

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
/**********************************************************************/
   // connect(谁,发生了什么信号,执行什么操作);
    //SIGNAL()函数信号类型
    //SLOT()函数选择槽函数
    connect(this->ui->button_in,SIGNAL(clicked(bool)),this,SLOT(cclogin()));
    connect(this->ui->button_out,SIGNAL(clicked(bool)),this,SLOT(cc_close()));
/**********************************************************************/
}

MainWindow::~MainWindow()
{
    delete ui;
}
/**********************************************************************/
//槽函数的实现
void MainWindow::cclogin()
{
    //qDebug() << "Login";//控制台输出打印
    //text()函数获取文本框中的内容
    //登录保护:避免登录多次失败扔可以登录
    static int Account_num = 0;
    QString name = this->ui->c_account->text();
    QString password = this->ui->c_password->text();
    if(name == "cc" && password == "123456")
    {
        //登录成功
        qDebug() << "登录成功";
    }else{
        //登录失败
        qDebug() << "登录失败";

        Account_num++;
        if(Account_num > 5)
        {
           // this->close();//登录5次失败就退出窗口程序
            disconnect(this->ui->button_in,SIGNAL(clicked(bool)),this,SLOT(cclogin()));登录5次失败就断开连接
        }
    }

}
void MainWindow::cc_close()
{
    this->close();//窗口关闭函数
    qDebug() << "窗口关闭";
}
/**********************************************************************/

第二种方法,通过ui设计师转到槽自动生成。

Qt窗口坐标系

以左上角为原点(0,0),X轴向右增加,Y轴向下增加。

自定义信号和槽

  • 返回值void
  • 都需要声明,信号函数不需要实现,槽函数必须实现
  • 可以有参数,可以重载
  • 信号不是必须连接槽,也可以信号连接信号。
  • 一个信号可以连接多个槽函数。
  • 多个信号可以连接同一个槽函数。
#include "widget.h"
#include "ui_widget.h"
// Teacher 类
//student 类
//老师出发一个信号,饿了,学生响应信号,吃饭

Widget::Widget(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::Widget)
{
    ui->setupUi(this);

    //创建一个老师对象
    this->te = new Teacher(this);
    //创建一个学生对象
    this->st = new Student(this);
    //饿了  吃饭连接
    connect(te,&Teacher::hungry,st,&Student::eat);

    //连接带参数的信号和槽
    //指针->地址
    //函数指针-> 函数地址
    void(Teacher::*teacherSignal)(QString) = &Teacher::hungry;
    void(Student::*studentSlot)(QString) = &Student::eat;
    connect(te,teacherSignal,st,studentSlot);
    //调用下课函数

    //调用下课函数
    ClassIsOver();
}

Widget::~Widget()
{
    delete ui;
}
void Widget::ClassIsOver()
{
    //下课函数,调用后触发老师 饿了 信号
    emit te->hungry();
}

/***************************************************************/
#ifndef TEACHER_H
#define TEACHER_H

#include 

class Teacher : public QObject
{
    Q_OBJECT
public:
    explicit Teacher(QObject *parent = 0);

signals:
    //自定义信号写的地方
    //返回值是void,只需要声明,不需要实现
    //可以有参数,可以重载
    void hungry();
    //信号重载版本
    void hungry(QString foodName);

public slots:
};

#endif // TEACHER_H
/***************************************************************/
#ifndef STUDENT_H
#define STUDENT_H

#include 

class Student : public QObject
{
    Q_OBJECT
public:
    explicit Student(QObject *parent = 0);

signals:

public slots:
    //返回值void,需要声明,也需要实现
    //可以有参数,可以反生重载
    void eat();
    //槽函数的重载版本
    void eat(QString foodName);
};

#endif // STUDENT_H
/***************************************************************/
#include "student.h"
#include
Student::Student(QObject *parent) : QObject(parent)
{

}
void Student::eat()
{
    qDebug() << "吃饭";
}
void Student::eat(QString foodName)
{
    //qDebug()<< "要吃什么"<char*
     //先转成QByteArray
    qDebug()<< "要吃什么"<

 

你可能感兴趣的:(Qt)