您的位置:首页 > 产品设计 > UI/UE

在DLL中使用duilib,并把ZIP皮肤编译进DLL中

2015-12-15 16:41 429 查看
转自: http://www.duilibcn.com/ziliao/240.html
在DLL中使用duilib,并把ZIP皮肤编译进DLL中



很显然,本文说明的目的是在DLL中使用duilib,并把ZIP皮肤编译进DLL中去。

首先你应该能建立一个在DLL中使用duilib的工程并且编译成功,而且duilib也应该是

静态编译的,这样最后生成的DLL才不会依赖其他无关的DLL和文件。



这里我只列出来关键代码,具体的代码可以在最后面的下载地址中找到。

class CMainWindow : public WindowImplBase

首先主窗体集成自WindowImplBase,并且不需要实现GetResourceID和GetResourceType,

否则加载DLL时程序会崩溃,谨记。

resource.h中定义ZIP文件的ID

#define IDR_SKIN1 10001



app.rc文件中定义ZIP的类型为SKIN,这里千万不要定义成ZIPRES。

IDR_SKIN1 SKIN "skin.zip"



下面列出main.cpp关键实现代码

#define EXPORT_API __declspec(dllexport)



DWORD g_func_GetResourceDataLength(HINSTANCE hInstance,

UINT dwResourceId,

const WCHAR* sResourceType)

{

if(hInstance == NULL)

return 0;



HRSRC hRsrc = FindResourceW(hInstance,MAKEINTRESOURCEW(dwResourceId), sResourceType);

if(!hRsrc)

{

::MessageBoxA(NULL,"hRsrc iS NULL","Fail",0);

return 0;

}

DWORD dwResSize = SizeofResource(hInstance,hRsrc);

FreeResource(hRsrc);

return dwResSize;

}



void g_func_GetResourceData(HINSTANCE hInstance,

UINT dwResourceId,

const WCHAR* sResourceType,

char* pRetData,

DWORD pRetLength)

{

if(hInstance == NULL)

return;



HRSRC hRsrc = FindResourceW(hInstance,MAKEINTRESOURCEW(dwResourceId),sResourceType);

if(!hRsrc)

{

return;

}



HGLOBAL hGlobal = (char*)LoadResource(hInstance,hRsrc);



char* pData = (char*)LockResource(hGlobal);

memcpy(pRetData,pData,pRetLength);



FreeResource(hRsrc);

}





extern "C" void EXPORT_API ShowDuiWindow()

{

HMODULE h = ::GetModuleHandleW(0);

CPaintManagerUI::SetInstance(h);



HMODULE hDll = ::GetModuleHandleW(L"untitled100.dll");



DWORD iLength = g_func_GetResourceDataLength(hDll,IDR_SKIN1,L"SKIN");

if(iLength > 0)

{

char* pData = (char*)malloc(iLength);

memset(pData,0,iLength);

g_func_GetResourceData(hDll,IDR_SKIN1,L"SKIN",pData,iLength);



CPaintManagerUI::SetResourceZip(pData,iLength);

}

else

{

::MessageBoxA(NULL,"Load Skin fail zip in rc size is 0","fail",0);

}



CMainWindow* pFrame = new CMainWindow(L"skin",L"CMainWindow.xml");



pFrame->Create(NULL,L" 你好 DuiLib",UI_WNDSTYLE_FRAME,WS_EX_WINDOWEDGE);

pFrame->CenterWindow();

pFrame->ShowModal();

}



关键代码分析

HMODULE h = ::GetModuleHandleW(0);

CPaintManagerUI::SetInstance(h);

设置实例句柄为主EXE的



HMODULE hDll = ::GetModuleHandleW(L"untitled100.dll");



DWORD iLength = g_func_GetResourceDataLength(hDll,IDR_SKIN1,L"SKIN");

if(iLength > 0)

{

char* pData = (char*)malloc(iLength);

memset(pData,0,iLength);

g_func_GetResourceData(hDll,IDR_SKIN1,L"SKIN",pData,iLength);



CPaintManagerUI::SetResourceZip(pData,iLength);

}

else

{

::MessageBoxA(NULL,"Load Skin fail zip in rc size is 0","fail",0);

}

g_func_GetResourceDataLength 和g_func_GetResourceData获取了rc中的ZIp数据

CPaintManagerUI::SetResourceZip(pData,iLength);则是把数据填充到了duilib需要的内容中去。

HMODULE hDll = ::GetModuleHandleW(L"untitled100.dll");则是提供获取rc数据时所需的DLL句柄

untitled100.dll是生成的DLL名称。



这样一来,就可以用duilib生成一个单一的DLL供其他程序调用了。

事实上duicreator 1.1.1已经包含了这个工程的模板。

源码下载:http://download.csdn.net/detail/hats8888/9358159
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: