资源路径:qt5插件方式封装7zip压缩解压缩-C++文档类资源-优快云下载
一、做个动态库,如Dll7Zip
pro 配置:
QT -= gui
TARGET = Dll7Zip
TEMPLATE = lib
DEFINES += DLL7ZIP_LIBRARY
# 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(release, debug|release){
DLLDESTDIR = ../bin64 # 将动态库dll放到bin4目录中
DESTDIR = ../lib64 # 将lib库放到lib64中
}
else:CONFIG(debug, debug|release){
DESTDIR = ../binDebug64
}
SOURCES += \
ZlibHelper.cpp
HEADERS += \
ZlibHelper.h \
callbackDef.h \
dll7zip_global.h
LIBS += -L$$PWD/../lib64 -lbit7z64 -lOleAut32 -lUser32 # 引入了第三库
INCLUDEPATH += $$PWD/../include # 包含第三方库的头文件
DEPENDPATH += $$PWD/../include
这里需要注意的地方是:
如果只做个动态库的话,可以定义信号。如果动态库最终是想封装成插件的话,就不要定义信号了,也可以定义信号,就是定义了插件也用不上,插件是不能发信号的。需要换成回调函数。
二、做个测试动态库的应用程序,如testDll7Zip
pro配置说明:
LIBS += -L$$PWD/../lib64 -lDll7Zip # 引入动态库
INCLUDEPATH += $$PWD/../Dll7Zip # 包含动态库目录
DEPENDPATH += $$PWD/../Dll7Zip
这里需要注意的地方是:
不要把Dll7Zip中的头文件直接添加到pro中了,如果头文件中有信号槽啥的会报错。就包含一下动态库目录就够了。
三、做个插件,如Dll7ZipPlugin
插件的pro配置:引入动态库部分的代码和第二步的写法一样,注意事项也和第二步一样。
3.1 接口头文件
#ifndef DLL7ZIPINTERFACE_H
#define DLL7ZIPINTERFACE_H
#include <QObject>
#include <QString>
#include "functional"
using namespace std;
typedef function<void(uint64_t nValue, uint64_t nTotalSize)>ProgressCallBack;
typedef function<void(QString sFile)>FileCallBack;
//定义接口
class Dll7ZipInterface
{
public:
virtual ~Dll7ZipInterface(){}
virtual QString extract(const QString& sZip, const QString& sDir) = 0; // 解压
virtual QString compress(const QString& sDir, const QString& sZip) = 0; // 压缩
virtual void setProgressCallBack(ProgressCallBack cb) = 0; // 压缩解压回调 过程
virtual void setFileCallBack(FileCallBack cb) = 0; // 压缩解压回调 文件
};
//一定是唯一的标识符
#define Dll7ZipInterface_iid "Examples.Plugin.Dll7ZipInterface"
QT_BEGIN_NAMESPACE
Q_DECLARE_INTERFACE(Dll7ZipInterface,Dll7ZipInterface_iid)
QT_END_NAMESPACE
#endif // DLL7ZIPINTERFACE_H
3.2 实现类头文件
#ifndef DLL7ZIPPLUGIN_H
#define DLL7ZIPPLUGIN_H
#include <QObject>
#include <QtPlugin>
#include "Dll7ZipInterface.h"
class Dll7ZipPlugin : public QObject,public Dll7ZipInterface
{
Q_OBJECT
Q_INTERFACES(Dll7ZipInterface)
Q_PLUGIN_METADATA(IID Dll7ZipInterface_iid FILE "qtplugin.json") // 注意源码文件下建个同名json后缀的空文件
public:
Dll7ZipPlugin();
QString extract(const QString& sZip, const QString& sDir) override; // 解压
QString compress(const QString& sDir, const QString& sZip) override; // 压缩
virtual void setProgressCallBack(ProgressCallBack cb) override; // 压缩解压回调 过程 // ProgressCallBack
virtual void setFileCallBack(FileCallBack cb) override; // 压缩解压回调 文件 // FileCallBack
private:
ProgressCallBack m_cbProgress;
FileCallBack m_cbFile;
};
#endif // DLL7ZIPPLUGIN_H
注意事项:
源码文件里要建个qtplugin.json的空文件
四、做个测试插件的应用程序
此时就可以不用在编译时加载动态库了,可以在运行时加载动态库插件,运行时找不到动态库插件可以提示报错,这也是插件的意义,根据需要加载,不需要主程序去编译。
#include "pluginUse/Dll7ZipInterface.h"
#include <QDir>
#include <QPluginLoader>
#include <QDebug>
PluginUser::PluginUser()
{
}
Dll7ZipInterface *PluginUser::loadDll7ZipPlugin()
{
QString sDllPath = "./plugins/Dll7ZipPlugin.dll";
sDllPath = QFileInfo(sDllPath).absoluteFilePath();
if (!QFile::exists(sDllPath))
{
m_sError = QString("%1 不存在").arg(sDllPath);
return nullptr;
}
QPluginLoader pluginLoader(sDllPath);
QObject *plugin = pluginLoader.instance();
Dll7ZipInterface* pInterface = qobject_cast<Dll7ZipInterface*>(plugin);
if(pInterface == nullptr)
{
m_sError = QString("插件加载失败 -- %1").arg(sDllPath);
}
return pInterface;
}
QString PluginUser::getError()
{
return m_sError;
}