QT DAY4
一、使用鼠标时间完成组件的移动
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include<QDebug>
#include<QMouseEvent>
QT_BEGIN_NAMESPACE
namespace Ui { class Widget; }
QT_END_NAMESPACE
class Widget : public QWidget
{
Q_OBJECT
public:
Widget(QWidget *parent = nullptr);
~Widget();
void mousePressEvent(QMouseEvent *event) override; //鼠标按下事件
void mouseMoveEvent(QMouseEvent *event) override; //鼠标移动事件
private:
Ui::Widget *ui;
QPoint drap; //定义Z向量
};
#endif // WIDGET_H
#include "widget.h"
#include "ui_widget.h"
Widget::Widget(QWidget *parent)
: QWidget(parent)
, ui(new Ui::Widget)
{
ui->setupUi(this);
//取消头部
this->setWindowFlag(Qt::FramelessWindowHint);
//qDebug()<<this->geometry().topLeft();
}
Widget::~Widget()
{
delete ui;
}
//鼠标按下事件的实现
void Widget::mousePressEvent(QMouseEvent *event)
{
qDebug()<<this->pos(); //是组件相对于整个屏幕的位置
qDebug()<<event->globalPos(); //是鼠标相对于整个屏幕的位置
if(event->buttons() == Qt::LeftButton)
{
drap = event->globalPos() - this->pos(); //求出相对于屏幕坐标系中,组件左上角位置到鼠标位置的向量
}else if(event->buttons() == Qt::RightButton)
{
this->close();
}
}
//鼠标移动事件的实现
void Widget::mouseMoveEvent(QMouseEvent *event)
{
this->move(event->globalPos() - drap); //将组件移动到新位置,由鼠标所在向量,减去组件左上角位置到鼠标位置的向量
}
二、定时器
当定时器时间超时后,就会有相关的动作进行相应,一个qt程序可以定义多个定时器,以处理不同的事情
定时器的实现有两种方式,分别是基于属性版本,和基于事件处理函数版本
1> 基于属性版本的定时器(QTimer),本质上是基于信号与槽
- 1、实例化一个QTimer类对象
- 2、调用该类对象中的成员函数start(毫秒数),启动一个定时器,并给定所定时长,那么该定时器会每隔给定时长后,发射timeout的信号
- 3、当时间超时后,那么该定时器就会自动发射一个timeout的信号
- 4、我们可以将该信号连接到自定义的槽函数中,在槽函数中处理相关逻辑
- 5、造成的现象是:每隔给定时长后,系统会自动调用槽函数
- 6、当不用该定时器时,可以使用该类中的成员函数stop停止一个定时器
2> 基于事件处理函数
- 1、基于事件处理函数,无需引入新的类对象,使用的全部都是自己的成员函数
- 2、调用自己的成员函数startTimer(毫秒数),启动一个定时器,启动之后,系统会每隔给定毫秒后,自动调用timerEvent函数
- 3、timerEvent函数也是自己类中继承的相关虚函数,所以,要对该函数进行重写
- 4、如果想要关闭定时器,只需调用自己的成员函数killTimer(定时器ID)
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include<QTimer> //定时器类
#include<QTime> //时间类
#include<QTimerEvent> //定时器事件类头文件
#include<QDateTime> //日期时间类
QT_BEGIN_NAMESPACE
namespace Ui { class Widget; }
QT_END_NAMESPACE
class Widget : public QWidget
{
Q_OBJECT
public:
Widget(QWidget *parent = nullptr);
~Widget();
//重写定时器事件处理函数
void timerEvent(QTimerEvent *event)override;
private slots:
void on_objStartBtn_clicked();
void timeout_slot(); //自定义处理timeout信号函数的声明
void on_eventStartBtn_clicked();
private:
Ui::Widget *ui;
//实例化一个定时器指针。基于类对象版本的定时器
QTimer *timer;
//定义一个定时器的id
int timer_id; //基于事件处理函数的定时器
};
#endif // WIDGET_H
三、绘制事件
QT界面运行时主要调用了绘制事件,将图形化界面绘制在计算机上
而绘制事件中调用时机是:第一次展示窗口、窗口因最大化、最小化恢复正常状态、窗口因被覆盖后再次暴露、更改窗口大小、调用update函数都会调用绘制事件
实现闹钟
#include "widget.h"
#include "ui_widget.h"
Widget::Widget(QWidget *parent)
: QWidget(parent)
, ui(new Ui::Widget)
{
ui->setupUi(this);
timer = new QTimer(this);
speecher = new QTextToSpeech(this);
// 初始化组件状态
ui->dateTimeEdit->setEnabled(true);
ui->action->setEnabled(true);
ui->stop->setEnabled(false);
ui->CurrentTime->setEnabled(false);
ui->edit1->setEnabled(true);
// 连接信号和槽
connect(timer, &QTimer::timeout, this, &Widget::timeout_slot);
connect(ui->action, &QPushButton::clicked, this, &Widget::on_action_clicked);
connect(ui->stop, &QPushButton::clicked, this, &Widget::on_stop_clicked);
}
Widget::~Widget()
{
delete ui;
}
void Widget::on_action_clicked()
{
// 启动定时器
timer->start(1000);
// 更新组件状态
ui->dateTimeEdit->setEnabled(false);
ui->action->setEnabled(false);
ui->stop->setEnabled(true);
ui->CurrentTime->setEnabled(true);
ui->edit1->setEnabled(false);
// 获取设定的时间
alarmTime = ui->dateTimeEdit->dateTime();
}
void Widget::timeout_slot()
{
QDateTime currentDateTime = QDateTime::currentDateTime();
QString t = currentDateTime.toString("yyyy-MM-dd hh:mm:ss");
// 更新UI上的时间显示
ui->CurrentTime->setText(t);
// 检查是否到达设定的时间
if (currentDateTime >= alarmTime) {
// 播报文本
speecher->say(ui->edit1->toPlainText());
// 停止定时器
timer->stop();
// 更新组件状态
ui->dateTimeEdit->setEnabled(true);
ui->action->setEnabled(true);
ui->stop->setEnabled(false);
ui->CurrentTime->setEnabled(false);
ui->edit1->setEnabled(true);
}
}
void Widget::on_stop_clicked()
{
// 停止定时器
timer->stop();
// 更新组件状态
ui->dateTimeEdit->setEnabled(true);
ui->action->setEnabled(true);
ui->stop->setEnabled(false);
ui->CurrentTime->setEnabled(false);
ui->edit1->setEnabled(true);
}