VC++资源,在一个静态的图书馆
-
22-08-2019 - |
题
是否有可能建立的资源进入一个静态的图书馆和重新使用它们通过简单的链接,与图书馆?
我主要考虑的情况下,你打电话的功能在库,这反过来访问的资源。
解决方案
这是可以做到的,但它相当痛苦:你不能这样通过简单的链接,与静态的图书馆。
考虑这样的:资源被埋在一个EXE或DLL。当一些代码中的静态图书馆的电话(例如)LoadIcon,它会得到的资源从EXE或DLL,它的链接。
所以,如果你的静态图书馆所需的资源可用,你已经有了几个选择:
- 你可以有所图书馆建立它们的飞行,然后使用(例如)
CreateDialogIndirect
.见雷蒙德*陈的 "建设一个对话的模板在运行时间". - 你可以把它们埋在图书馆作为简单的阵列(即)
char my_dialog_resource[] = { .... };
, ,然后使用(例如)CreateDialogIndirect
.你可能会需要找到(或写)一个实用工具,将从.RES
的文件.CPP
文件。 - 你可以船舶的LIB文件与资源脚本(
.RC
文件)和相应的标题的文件。然后你#include
它们作为相关。你会需要保留的范围的资源Id LIB使用,使他们不碰撞的那些主要EXE或DLL。这是什么MFC不当使用作为一个静态的图书馆。或者您可以使用的字符串资源代码(这不起作用STRINGTABLE
资源)。 - 你的静态图书馆可以运用一个单独的资源DLL。
其他提示
你唯一需要做的,以使用的资源(图像的对话,等等)在一个静态的图书馆视C++(2008年), 包括静态图书馆的关联。res文件 在您的项目。这可以通过在"项目设置/连接输入/其他依赖关系".
这种解决方案,资源的静态图书馆被包装成。exe,所以你不需要一个额外的DLL。令人遗憾的是,Visual Studio不包括.res文件自动的,因为它并。lib文件(当使用"的项目相关性"特征),但我认为这个小小的额外的步骤是可以接受的。
我已经看过了很长的时间为这一解决方案,而现在它让我吃惊就是这么简单。唯一的问题是,它是完全没有证件。
我刚刚经历了这MS Visual Studio编译器。我们将一些旧的项目从Dll到静态的图书馆。几个这些Dll了对话或串资源嵌入其中。我能够编制的。RC脚本,这些Dll入我们的主要应用程序通过包括他们在主要的应用程序的第RC脚本文件通过的"TEXTINCLUDE"的机制。我发现,它最容易这样做的编辑RC文件直接,但Visual Studio提供了一个稍微更多的"wizardy"机制。执行是最有可能不同于其他编译器。
操纵的主要RC脚本。
.1.在"2TEXTINCLUDE"部分,包括标题文件,该文件界定的资源标识你的图书馆。语法
2 TEXTINCLUDE
BEGIN
"#include ""my_first_lib_header.h""\r\n"
"#include ""my_second_lib_header.h""\0"
END
.2.在"3TEXTINCLUDE"部分,包括RC脚本从你的图书馆。
3 TEXTINCLUDE
BEGIN
"#include ""my_first_library.rc""\r\n"
"#include ""my_second_library.rc""\0"
END
步骤3和4应自动发生,但是我发现这是更可靠刚刚进入他们自己,而不是取决于微软的资源脚本编译器,以照顾的东西。
.3.添加的标题的文件有你的图书馆资源的定义来读唯一的符号的清单。这个名单通常是在靠近顶部的文件。
#define APSTUDIO_READONLY_SYMBOLS
#include "my_first_lib_header.h"
#include "my_second_lib_header.h"
#undef APSTUDIO_READONLY_SYMBOLS
.4.包括图书馆的第RC脚本APSTUDIO_INVOKED部分。这通常是在底部的文件。
#ifndef APSTUDIO_INVOKED
#include "my_first_library.rc"
#include "my_second_library.rc"
#endif
你也可以做所有这一切都自动通过visual studio IDE,但我发现它并不总是应用时,我预期它。
- 打开"资源图"窗在视觉工作室。
- 右侧击你的主要应用程序的资源文件和选择"资源包括..."从上下文的菜单。
- 在该一栏"只读符号指令,"加入的包括报表。h文件界定的资源标识是为了你的图书馆。
- 在箱标有"编译时指令,"加入的包括报表你的图书馆。rc脚本。
- 点击没关系。你可能还需要手动触发RC脚本汇编,以确保它发生。
如果你的图书馆的资源脚本引用的任何磁盘上的文件(文本文件的图标文件等), 你会需要确保主要的应用程序项目知道在哪里可以找到他们。你可以复制这些文件的某个地方应用程序可以找到他们或者您可以添加一个额外的包括路径的编译器的设定。
增加一个额外的包括路径:
- 开放性对话对你的主要应用程序。
- 选择"结构性的/资源/大"从左边的导航格中。
- 在性清单,输入任何有关道路旁的"附加包括的目录。"
我不这么认为。静态库不具有它自己的HINSTANCE。它的代码在DLL或EXE的哪个环节它的上下文中执行。这就是为什么所有的资源,你会尝试从静态库的代码加载将是封闭的DLL / EXE的。
我没有那样的资源与DLL重用不过,只要它有它自己的地址空间,并且可以调用LoadResource与DLL的HINSTANCE。
为每Visual Studio2010年,开发工具,从微软显然无法适当地处理编成资源数据的内的静态图书馆。
分发了编制资源文件(a .res
文件),你有两个选择:
- 分发
.res
文件分开,并指示客户的代码链接针对它们; - 使用
cvtres
合并几个.res
文件合并成一个单一的对象(.obj
)的文件,并提供它分开。
注意,你不能lib在目文件的创建 cvtres
.如果有多个目文件提供, lib
抱怨如,虽然多 .res
文件;如果一个单一的目文件提供, lib
不抱怨,但接头的只是忽略了嵌入的资源数据库文件。
它可能的情况下,有一种方法可以力连接读取和链接的感慨资源数据(与某些命令行的选择,节操纵,等等),由于资源的数据是事实上在图书馆(如 dumpbin
揭示的).迄今为止,我还没有找到一个解决方案,并且,除非一个愿意黑客的开发工具,更好的东西,比这简单的解决方案可能是不值得的努力。
唯一的办法对船舶的资源数据在一个静态的图书馆(在这种情况下, 与 静态图书馆)是分配的资源单独和明确的链接,它们在客户代码。使用 cvtres
数量可以减少分发的资源文件之一,如果你有很多。
的推荐方法是一起提供与资源一个dll与库中。
在以下方法使用的任何资源(在这个例子中,一个图标)可以作为一个整体部分的一个静态的图书馆,这种图书馆能够使用的任何类型的应用程序,包括控制台之一(其中没有任何资源段的任何责任).
- 图标转化为一个静态阵列的字节。 bin2c 可以使用。
数据转换成一个波浪型处理。这里是我怎么做:
HICON GetIcon() { DWORD dwTmp; int offset; HANDLE hFile; HICON hIcon = NULL; offset = LookupIconIdFromDirectoryEx(s_byIconData, TRUE, 0, 0, LR_DEFAULTCOLOR); if (offset != 0) { hIcon = CreateIconFromResourceEx(s_byIconData + offset, 0, TRUE, 0x00030000, 0, 0, LR_DEFAULTCOLOR | LR_DEFAULTSIZE); } return hIcon; }
GetIcon而不是使用LoadIcon.而不是呼吁:
m_hIcon = ::LoadIcon(hInstanceIcon, MAKEINTRESOURCE(pXMB->nIcon));
然后打电话
m_hIcon = GetIcon()