9.5 监视文件和目录的变化
9.5 监视文件和目录的变化
我们前面讲了如何通过QTextStream、QDataStream、QDir以及QFileInfo来获取文件的信息,但在实际的开发当中,我们往往需要对某些文件或目录进行一些读写操作,但往往在读写操作之前需要先对文件或目录的状态进行一个监控。以确保文件的实时状态。那么实际上在Qt中也有这样的类来监控文件或目录的实时状态,这个类就是所谓的QFileSystemWatcher。这个类可以通过例如addPath()来添加对单个目录的监视,也可以通过addPaths()来对多个目录的监视。如果想移除不需要的目录,那么就可以使用removePath()或removePaths()来移除不需要监视的目录。接下来我们通过一个案例来说明QFileSystemWatcher的使用。
案例:使用QFileSystemWatcher来监视指定的目录。
(1)新建Qt的GUI项目,项目名称为FileWatcher,将类名命名为Watcher,并将该类继承自QWidget类。不需要创建ui文件。
(2)在watcher.h中添加以下成员,完成对界面基本的元素的布置以及必要的数据成员的声明。
#ifndef WATCHER_H
#define WATCHER_H
#include <QWidget>
#include <QDataStream>
#include <QDebug>
#include <QTextStream>
#include <QDir>
#include <QFileDialog>
#include <QMessageBox>
#include <QPushButton>
#include <QFileSystemWatcher>
#include <QFileInfo>
#include <QListWidget>
#include <QGridLayout>
#include <QFileInfoList>
class Watcher : public QWidget
{
Q_OBJECT
public:
Watcher(QWidget *parent = nullptr);
~Watcher();
private slots:
void slotAddPath();
void slotRemovePath();
private slots:
void slotdirectoryChanged(const QString& path);
private:
QPushButton*m_addPathPushButton;
QPushButton*m_removePathPushButton;
QListWidget*m_pathListWidget;
QList<QListWidgetItem*>m_listItem;
private:
QFileSystemWatcher*m_watcher;
private:
QGridLayout*m_mainLayout;
};
#endif // WATCHER_H
(3)在watcher.cpp中进行实现
#include "watcher.h"
Watcher::Watcher(QWidget *parent):QWidget(parent)
{
this->setWindowTitle(QString("目录监视器"));
m_watcher = new QFileSystemWatcher;
m_addPathPushButton = new QPushButton("添加目录");
m_removePathPushButton = new QPushButton("移除目录");
m_pathListWidget = new QListWidget;
m_mainLayout = new QGridLayout(this);
m_mainLayout->addWidget(m_pathListWidget,0,0);
m_mainLayout->addWidget(m_addPathPushButton,0,1);
m_mainLayout->addWidget(m_removePathPushButton,0,2);
connect(this->m_addPathPushButton,&QPushButton::clicked,this,&Watcher::slotAddPath);
connect(this->m_removePathPushButton,&QPushButton::clicked,this,&Watcher::slotRemovePath);
connect(this->m_watcher,&QFileSystemWatcher::directoryChanged,this,&Watcher::slotdirectoryChanged);
}
Watcher::~Watcher()
{
delete m_mainLayout;
m_mainLayout = nullptr;
delete m_pathListWidget;
m_pathListWidget = nullptr;
delete m_addPathPushButton;
m_addPathPushButton = nullptr;
delete m_removePathPushButton;
m_removePathPushButton = nullptr;
delete m_watcher;
m_watcher = nullptr;
}
void Watcher::slotAddPath()
{
QString path = QFileDialog::getExistingDirectory(this,QString("选择一个目录"),"./");
if(path.isEmpty())
{
QMessageBox::warning(this,QString("提示"),QString("未选择任何目录!"));
}
else
{
for(int i = 0;i < m_pathListWidget->count();++i)
{
if(m_pathListWidget->item(0)->text() == path)
{
QMessageBox::information(this,QString("提示"),QString("该目录已存在!"));
return;
}
}
m_pathListWidget->addItem(path);
m_watcher->addPath(path);
}
}
void Watcher::slotRemovePath()
{
//如果没有item,不能移除
if(0 == m_pathListWidget->count())
{
QMessageBox::warning(this,QString("提示"),QString("没有任何的目录,无法移除!"));
}
else
{
//获取到选中的目录的item
QList<QListWidgetItem*>list = m_pathListWidget->selectedItems();
for(int i = 0;i < list.count();i++)
{
QListWidgetItem*item = m_pathListWidget->takeItem(m_pathListWidget->row(list.at(i)));
m_watcher->removePath(item->text());
list.removeAt(i);
delete item;
item = nullptr;
}
}
}
void Watcher::slotdirectoryChanged(const QString &path)
{
QMessageBox::information(this,QString("提示"),QString("%1中的内容发生了变化!").arg(path));
}
(4)运行,当我们添加桌面这个目录进行监视时,我们在桌面创建一个文件或文件夹时,就会出现提示窗口

(5)对QFileSystemWatcher的一些总结
//对于QFileSystemWatcher这个类,它的成员都较为简单,这里就只简单做一个说明,这些成员看起来都非常的简单易懂。 //1.构造器 //QFileSystemWatcher::QFileSystemWatcher(const QStringList &paths, QObject *parent = nullptr)//构造一个对多个path目录进行监视的Watcher对象,这里面使用了StringList来存储这些需要被监视的目录 //QFileSystemWatcher::QFileSystemWatcher(QObject *parent = nullptr)//构造一个空的,但指定基类的空的Watcher对象 //2.bool QFileSystemWatcher::addPath(const QString &path) //该函数用于往Watcher中添加一个目录进行监视,如果目录不存在或者是已经有这个目录在被监视了,就会返回false //3.QStringList QFileSystemWatcher::addPaths(const QStringList &paths) //该函数用于一次性添加多个目录进行监视,会返回没有被监视的目录(也就是已经被添加过的,或者是目录不存在的) //4.QStringList QFileSystemWatcher::directories() const //返回此时此刻正在被监视的目录列表 //5.QStringList QFileSystemWatcher::files() const //返回此时此刻正在被监视的文件列表 //6.bool QFileSystemWatcher::removePath(const QString &path) //从被监视的目录中移除指定的目录,不对其进行监视,返回true则移除成功,否则移除失败 //7.QStringList QFileSystemWatcher::removePaths(const QStringList &paths) //从被监视的目录中移除多个目录,并返回没有被成功移除的目录的列表 //信号 //void directoryChanged(const QString &path)//当目录中的内容发生改变时,会发出此信号,参数就是哪个目录中的内容发生了变化 //void fileChanged(const QString &path)//当文件的内容发生了变化时,会发出此信号,参数为哪个文件的内容发生了改变
本节代码:https://files.cnblogs.com/files/blogs/792763/FileWatcher.zip?t=1720263231&download=true

浙公网安备 33010602011771号