MFC动态调用2种不同的QT DLL库

MFC中写法:

1、调用DLL接口类 ,下列代码不是完整的,但是功能能满足

xxx.h

HMODULE m_hDLL;

// 加载DLL
    bool LoadDll(char* strDLLFileName);

// 实例化接口
    int CreateInstance(int argc, char *argv[]);

//启动QT主线程,阻塞
    int StartCoreApplication();

//获得QT DLL中实例化的类
    void* GetInstance(); 

// 释放接口实例
    void ReleaseInstance(void* &pInterface);

xxx.cpp

typedef  int(__cdecl *Func_CreateObject)(int argc, char *argv[]);
typedef  int(__cdecl *Func_StartCoreApplication)();
typedef  void*(__cdecl *Func_GetObject)();
typedef  void(__cdecl *Func_ReleaseObject)(void*&);

// 加载DLL
bool xxx::LoadDll(char* strDLLFileName)
{
    CString strInfo;
    m_csFileName = strDLLFileName;
    m_hDLL = ::LoadLibrary(strDLLFileName);
    if (m_hDLL == 0)
        return false;
    }
    return true;
}

// 实例化接口
int xxx::CreateInstance(int argc, char *argv[])
{
    int pReturn = 0;
    if (m_hDLL != NULL)
    {
        Func_CreateObject funcCreateObject = (Func_CreateObject)GetProcAddress(m_hDLL, "WD_CreateObject");
        pReturn = funcCreateObject(argc, argv);
    }
    return pReturn;
}

//启动QT主线程
int xxx::StartCoreApplication()
{
    int pReturn = 0;
    if (m_hDLL != NULL)
    {
        Func_StartCoreApplication funcStartCoreApplication = (Func_StartCoreApplication)GetProcAddress(m_hDLL, "WD_StartCoreApplication");
		pReturn = funcStartCoreApplication();
    }
    return pReturn;
}

void* xxx::GetInstance()
{
    void* pReturn = nullptr;
    if (m_hDLL != NULL)
    {
        Func_GetObject funcGetObject = (Func_GetObject)GetProcAddress(m_hDLL, "WD_GetObject");
		pReturn = funcGetObject();
    }
    return pReturn;
}

// 释放接口实例
void xxx::ReleaseInstance(void* &pInterface)
{
    if (m_hDLL != NULL)
    {
        if (pInterface != NULL)
        {
            Func_ReleaseObject funcReleaseObject = (Func_ReleaseObject)GetProcAddress(m_hDLL, "WD_ReleaseObject");
            funcReleaseObject(pInterface);
        }
    }
}

2、在MFC中调用的,本次演示同时调用2个DLL

aaa.h

xxx m_Factory1;//接口工厂1
xxx m_Factory2;//接口工厂2

QtObject1_interface* qtObject1;  //此对象是带纯虚函数的结构体接口,在QT DLL实例化类中可以Public继承,通过GetInstance()获取实例化类指针强转调用函数
QtObject2_interface* qtObject2; //同上

static DWORD WINAPI ThreadFunc(void* pParam);//QT有主线程,MFC开启线程去调用QT

aaa.cpp

//初始化和启动MFC线程

m_Factory1.LoadDll("QtObject1Lib.dll");
m_Factory2.LoadDll("QtObject2Lib.dll");
DWORD m_dwThreadID;
 ::CreateThread(NULL, 0, &ThreadFunc, this, 0, &m_dwThreadID);

//MFC线程

DWORD WINAPI aaa::ThreadFunc(void* pParam)
{
    aaa* m_p = (aaa*)pParam;
    m_p->m_Factory1.CreateInstance(0, nullptr);
    m_p->m_Factory2.CreateInstance(0, nullptr);
    m_p->m_Factory1.StartCoreApplication();//只需要调用1个DLL启动QT核心线程
    return 0;
}

//调用QT类函数

qtObject1= (QtObject1_interface*)m_Factory1.GetInstance();//获得DLL1的实例化类

qtObject2= (QtObject2_interface*)m_Factory2.GetInstance();//获得DLL2的实例化类

int a = qtObject1.ceshi1(a,b,c,....);//调用DLL1实例化类继承的结构体虚函数ceshi1

int b = qtObject2.ceshi2(a,b,c,....);//调用DLL2实例化类继承的结构体虚函数ceshi2

MFC和QT公用的接口

QtObject1_interface.h

struct QtObject1_interface
{
public:
    virtual int __cdecl ceshi1(a, b, c,........) = 0;
};

---------------分界线,以上MFC部分代码已经全部写完----------------------------------

QT中的写法

1、创建QT Library C++工程

QtObject1Lib.h

extern "C" __declspec(dllexport) int __cdecl WD_CreateObject(int argc, char *argv[]);
extern "C" __declspec(dllexport) int __cdecl WD_StartCoreApplication();
extern "C" __declspec(dllexport) void *__cdecl WD_GetObject();
extern "C" __declspec(dllexport) void __cdecl WD_ReleaseObject(void *&pObj);

QtObject1Lib.cpp

static void *pObj = nullptr;
__declspec(dllexport) int __cdecl WD_CreateObject(int argc, char *argv[], IAPP_Stream *pStreamOut)
{
    QCoreApplication *app = QCoreApplication::instance();
    if (app == nullptr) {
        app = new QCoreApplication(argc, argv);
    }
    pObj = (QtObject1_interface*) new QTobject1();
    qDebug() << "Creat QTobject1 object success!";
    return 0;
}

__declspec(dllexport) int __cdecl WD_StartCoreApplication()
{
    QCoreApplication *app = QCoreApplication::instance();
    qDebug() << "Start QtCoreApplication thread success, Don't start repeatedly!";
    return app->exec();
}

__declspec(dllexport) void *__cdecl WD_GetObject()
{
    return pObj;
}

__declspec(dllexport) void __cdecl WD_ReleaseObject(void *&pObj)
{
    if (pObj != nullptr) {
        QTobject1*pObj1 = (QTobject1*) pObj;
        delete pObj1;
        pObj1 = nullptr;
        pObj = nullptr;
    }
}

2、创建需要调用的类

QTobject1.h

class QTobject1: public QObject, QTobject1_interface
{
    Q_OBJECT
public:
    explicit QTobject1(QObject *parent = nullptr);

    // QTonject1_interface interface
public:
    int __cdecl ceshi1(a, b, c,......);

QTobject1.cpp

QTobject1::QTobject1(QObject *parent)
{
   
}

int QTobject1::ceshi1(a, b, c,....)
{
    return 0;
}

---------------分界线,以上QT部分代码已经全部写完----------------------------------

至此,MFC调用QT DLL可以实现并且QT内部信号和槽都可以使用,QT的主线程已经启动。

猜你喜欢

转载自blog.csdn.net/woshileihuanji/article/details/107740709