QPluginLoader 实例 returns 空
QPluginLoader instance returns null
问候
我用 Qt (5.6.2)
创建了插件并尝试加载它,但它一直 returns null
。我检查了几个问题并尝试了解决方案,但它对我不起作用。
你能看看下面的代码,看看有什么问题吗?
DeviceManager.hpp
#ifndef DEVICE_MANAGER_HPP
#define DEVICE_MANAGER_HPP
#include <QtCore>
#include <string>
using namespace std;
class DeviceManager
{
public:
virtual ~DeviceManager() {}
virtual bool initialize() = 0;
virtual string getBrandName() = 0;
};
QT_BEGIN_NAMESPACE
Q_DECLARE_INTERFACE(DeviceManager, "com.some.address/1.0")
QT_END_NAMESPACE
#endif //DEVICE_MANAGER_HPP
DeviceManagerImpl.hpp
#ifndef DEVICE_MANAGER_IMPL_HPP
#define DEVICE_MANAGER_IMPL_HPP
#include "DeviceManager.hpp"
#include <string>
using namespace std;
class DeviceManagerImpl : public QObject, public DeviceManager
{
Q_OBJECT
Q_PLUGIN_METADATA(IID "com.some.address/1.0")
Q_INTERFACES(DeviceManager)
public:
DeviceManagerImpl();
//Override Method
bool initialize(); //Have implementation in cpp file
string getBrandName(); //Have implementation in cpp file
private:
...
};
#endif //DEVICE_MANAGER_IMPL_HPP
Pro 文件
QT += core gui sql
TARGET = Device-Manager
#TARGET = $$qtLibraryTarget(Device-Manager)
TEMPLATE = lib
CONFIG += plugin
SOURCES += \
...
HEADERS += \
...
DISTFILES += Device-Manager.json
unix {
target.path = /usr/lib
INSTALLS += target
}
这就是我尝试在主进程中加载插件的方式。
QPluginLoader * pluginLoader = new QPluginLoader(pluginPath.c_str());
QObject * plugin = pluginLoader->instance();
if (plugin)
{
deviceManager = qobject_cast<DeviceMAnager *>(plugin);
return true;
}
else
{
delete pluginLoader;
return false;
}
我正在使用 QT 5.6.2 和 QT Creator 以及 MinGW 32 位。
编辑 1:
我找到了原因,但我不知道为什么会导致问题,我使用链接到项目的库但是当我使用它的函数时,实例 returns null.
LIBS += $$(STANDARD_XFS_DIRECTORY)/LIB/MSXFS.lib
INCLUDEPATH += $$(STANDARD_XFS_DIRECTORY)/INCLUDE
我也没有编译或链接器错误。谁能告诉我这里出了什么问题?
编辑 2:
当我使用 Visual Studio
制作项目时,CMakeList.txt
中的库和插件的以下配置工作得很好。 (使用 CMake 制作)
ADD_DEFINITIONS(${QT_DEFINITIONS})
ADD_DEFINITIONS(-DUNICODE -D_UNICODE)
ADD_DEFINITIONS(-DQT_PLUGIN)
ADD_DEFINITIONS(-DQT_SHARED)
ADD_DEFINITIONS(-DQT_DLL)
ADD_DEFINITIONS(-DQT_LARGEFILE_SUPPORT)
ADD_DEFINITIONS(-DQT_THREAD_SUPPORT)
INCLUDE_DIRECTORIES(
${STANDARD_XFS_DIRECTORY}/INCLUDE
)
LINK_DIRECTORIES(
${STANDARD_XFS_DIRECTORY}
${STANDARD_XFS_DIRECTORY}/LIB
)
SET(XFS_LIBS
MSXFS
xfs_conf
SSIDLL
)
TARGET_LINK_LIBRARIES(Device-Manager
${XFS_LIBS}
)
这是 .pro
文件中 Qt Creator
和 MinGW
中库和插件的配置,当我使用该库时它不起作用。
QT -= gui
QT += core sql
TARGET = Device-Manager
TEMPLATE = lib
CONFIG += plugin
CONFIG += c++11
DEFINES += DEVICEMANAGER_LIBRARY
INCLUDEPATH += $$(STANDARD_XFS_DIRECTORY)
INCLUDEPATH += $$(STANDARD_XFS_DIRECTORY)/INCLUDE
message(Include : $${INCLUDEPATH})
LIBS += $$(STANDARD_XFS_DIRECTORY)/SSIDLL.lib
LIBS += $$(STANDARD_XFS_DIRECTORY)/LIB/MSXFS.lib
LIBS += $$(STANDARD_XFS_DIRECTORY)/LIB/xfs_conf.lib
message(Lib : $${LIBS})
所以我可以说它自己的代码很好,我肯定在 .pro
文件中缺少一些配置。
PS1:插件和加载插件的应用程序,它们的pro文件中都有INCLUDEPATH
和LIBS
库。
PS2: 应用程序和插件都处于调试模式
PS3: 我在编译期间没有遇到任何编译错误或链接器错误。
编辑 3:
我制作了简单的控制台应用程序并包含了我的库头文件和 lib 文件并调用了该函数,这是我在 运行 该应用程序时遇到的错误。所以一定是这样。但说真的为什么!!!
代码:
LPWFSRESULT result = new WFSRESULT();
WFSFreeResult(result);
PS:该库来自可靠来源,可与 Visual Studio.
完美配合
提前致谢。
只要适当地阅读帖子,有时可以开阔眼界。
问题是:您将 minGW 与 Qt 一起使用,但使用的是 lib 文件,即使用 msvc 编译器 (visual studio) 编译的库。这是不可能的,因为它们通常不兼容!
你现在有 2 个选择:要么你为任何版本的 Visual Studio 编译库安装 Qt 工具包,要么,如果库是开源的,使用 mingw 自己编译它。
好吧,我发现了问题,但是它太愚蠢了。我 运行 投影 windows 10 32 位并且工作正常。也许是某些与 64 位不兼容的东西导致了这个混乱。
感谢大家提供的所有解决方案,希望您的解决方案能帮助其他人解决问题。
非常感谢!
问候
我用 Qt (5.6.2)
创建了插件并尝试加载它,但它一直 returns null
。我检查了几个问题并尝试了解决方案,但它对我不起作用。
你能看看下面的代码,看看有什么问题吗?
DeviceManager.hpp
#ifndef DEVICE_MANAGER_HPP
#define DEVICE_MANAGER_HPP
#include <QtCore>
#include <string>
using namespace std;
class DeviceManager
{
public:
virtual ~DeviceManager() {}
virtual bool initialize() = 0;
virtual string getBrandName() = 0;
};
QT_BEGIN_NAMESPACE
Q_DECLARE_INTERFACE(DeviceManager, "com.some.address/1.0")
QT_END_NAMESPACE
#endif //DEVICE_MANAGER_HPP
DeviceManagerImpl.hpp
#ifndef DEVICE_MANAGER_IMPL_HPP
#define DEVICE_MANAGER_IMPL_HPP
#include "DeviceManager.hpp"
#include <string>
using namespace std;
class DeviceManagerImpl : public QObject, public DeviceManager
{
Q_OBJECT
Q_PLUGIN_METADATA(IID "com.some.address/1.0")
Q_INTERFACES(DeviceManager)
public:
DeviceManagerImpl();
//Override Method
bool initialize(); //Have implementation in cpp file
string getBrandName(); //Have implementation in cpp file
private:
...
};
#endif //DEVICE_MANAGER_IMPL_HPP
Pro 文件
QT += core gui sql
TARGET = Device-Manager
#TARGET = $$qtLibraryTarget(Device-Manager)
TEMPLATE = lib
CONFIG += plugin
SOURCES += \
...
HEADERS += \
...
DISTFILES += Device-Manager.json
unix {
target.path = /usr/lib
INSTALLS += target
}
这就是我尝试在主进程中加载插件的方式。
QPluginLoader * pluginLoader = new QPluginLoader(pluginPath.c_str());
QObject * plugin = pluginLoader->instance();
if (plugin)
{
deviceManager = qobject_cast<DeviceMAnager *>(plugin);
return true;
}
else
{
delete pluginLoader;
return false;
}
我正在使用 QT 5.6.2 和 QT Creator 以及 MinGW 32 位。
编辑 1: 我找到了原因,但我不知道为什么会导致问题,我使用链接到项目的库但是当我使用它的函数时,实例 returns null.
LIBS += $$(STANDARD_XFS_DIRECTORY)/LIB/MSXFS.lib
INCLUDEPATH += $$(STANDARD_XFS_DIRECTORY)/INCLUDE
我也没有编译或链接器错误。谁能告诉我这里出了什么问题?
编辑 2:
当我使用 Visual Studio
制作项目时,CMakeList.txt
中的库和插件的以下配置工作得很好。 (使用 CMake 制作)
ADD_DEFINITIONS(${QT_DEFINITIONS})
ADD_DEFINITIONS(-DUNICODE -D_UNICODE)
ADD_DEFINITIONS(-DQT_PLUGIN)
ADD_DEFINITIONS(-DQT_SHARED)
ADD_DEFINITIONS(-DQT_DLL)
ADD_DEFINITIONS(-DQT_LARGEFILE_SUPPORT)
ADD_DEFINITIONS(-DQT_THREAD_SUPPORT)
INCLUDE_DIRECTORIES(
${STANDARD_XFS_DIRECTORY}/INCLUDE
)
LINK_DIRECTORIES(
${STANDARD_XFS_DIRECTORY}
${STANDARD_XFS_DIRECTORY}/LIB
)
SET(XFS_LIBS
MSXFS
xfs_conf
SSIDLL
)
TARGET_LINK_LIBRARIES(Device-Manager
${XFS_LIBS}
)
这是 .pro
文件中 Qt Creator
和 MinGW
中库和插件的配置,当我使用该库时它不起作用。
QT -= gui
QT += core sql
TARGET = Device-Manager
TEMPLATE = lib
CONFIG += plugin
CONFIG += c++11
DEFINES += DEVICEMANAGER_LIBRARY
INCLUDEPATH += $$(STANDARD_XFS_DIRECTORY)
INCLUDEPATH += $$(STANDARD_XFS_DIRECTORY)/INCLUDE
message(Include : $${INCLUDEPATH})
LIBS += $$(STANDARD_XFS_DIRECTORY)/SSIDLL.lib
LIBS += $$(STANDARD_XFS_DIRECTORY)/LIB/MSXFS.lib
LIBS += $$(STANDARD_XFS_DIRECTORY)/LIB/xfs_conf.lib
message(Lib : $${LIBS})
所以我可以说它自己的代码很好,我肯定在 .pro
文件中缺少一些配置。
PS1:插件和加载插件的应用程序,它们的pro文件中都有INCLUDEPATH
和LIBS
库。
PS2: 应用程序和插件都处于调试模式
PS3: 我在编译期间没有遇到任何编译错误或链接器错误。
编辑 3:
我制作了简单的控制台应用程序并包含了我的库头文件和 lib 文件并调用了该函数,这是我在 运行 该应用程序时遇到的错误。所以一定是这样。但说真的为什么!!!
代码:
LPWFSRESULT result = new WFSRESULT();
WFSFreeResult(result);
PS:该库来自可靠来源,可与 Visual Studio.
完美配合提前致谢。
只要适当地阅读帖子,有时可以开阔眼界。
问题是:您将 minGW 与 Qt 一起使用,但使用的是 lib 文件,即使用 msvc 编译器 (visual studio) 编译的库。这是不可能的,因为它们通常不兼容!
你现在有 2 个选择:要么你为任何版本的 Visual Studio 编译库安装 Qt 工具包,要么,如果库是开源的,使用 mingw 自己编译它。
好吧,我发现了问题,但是它太愚蠢了。我 运行 投影 windows 10 32 位并且工作正常。也许是某些与 64 位不兼容的东西导致了这个混乱。
感谢大家提供的所有解决方案,希望您的解决方案能帮助其他人解决问题。
非常感谢!