我正在编写一个C ++程序,该程序需要处理大块数据,尤其是文本文件,但是数据长于给定的字符串限制。结果,我试图将文本文件加载为资源文件,但是,每当我调用FindResource时,响应都是一个空句柄。
我已经遍历了其他堆栈溢出帖子,并且MSDN尝试正确实现此功能,但是我尝试过的任何操作都没有返回有效的句柄。
C ++代码:
HGLOBAL res_handle = NULL;
HRSRC res;
char * res_data;
DWORD res_size;
auto g_hInstance = GetModuleHandle(NULL);
res = FindResource(g_hInstance, MAKEINTRESOURCE(MY_RESOURCE), RT_RCDATA);
std::cout << res << std::endl;
std::cout << GetLastError() << std::endl;
res_handle = LoadResource(NULL, res);
std::cout << GetLastError() << std::endl;
res_data = (char*)LockResource(res_handle);
std::cout << GetLastError() << std::endl;
res_size = SizeofResource(NULL, res);
std::cout << GetLastError() << std::endl;
输出:
0000000000000000
1813
87
87
87
Resource.h:
//{{NO_DEPENDENCIES}}
// Microsoft Visual C++ generated include file.
// Used by Resource.rc
//
#define MY_RESOURCE 300
// Next default values for new objects
//
#ifdef APSTUDIO_INVOKED
#ifndef APSTUDIO_READONLY_SYMBOLS
#define _APS_NEXT_RESOURCE_VALUE 103
#define _APS_NEXT_COMMAND_VALUE 40002
#define _APS_NEXT_CONTROL_VALUE 1001
#define _APS_NEXT_SYMED_VALUE 101
#endif
#endif
Resource.rc:
MY_RESOURCE RCDATA "C:\\Users\\foobar\\Desktop\\projects\\foobar\\test0.txt"
答案 0 :(得分:0)
当您从GetLastError()收到错误代码时,您应该调用FormatMessage API(带有FORMAT_MESSAGE_FROM_SYSTEM
标志)或在Visual Studio中使用错误查找工具“工具/错误查找”。
代码1813转换为以下消息:“在图像文件中找不到指定的资源类型。”
如您所见,它抱怨资源类型。
我认为您不需要RCDATA。从16位窗口开始,它已经很旧了。在Win32中,自定义资源类型是字符串,而不是整数。 IDE甚至不支持RCDATA。
正确的方法-右键单击.rc文件,“添加资源”,“导入”,浏览要包含的文件,Visual Studio会询问您资源类型,并写任何字符串,例如text
将执行此操作,然后将该字符串作为FindResource函数的最后一个参数传递。如果使用默认项目设置进行构建,则它是Unicode,因此您需要在此处传递Unicode字符串L"text"
。
答案 1 :(得分:0)
这对我有用。我怀疑您的构建设置有问题。
我从Visual Studio 2017中的一个空项目开始,我在项目设置中唯一更改的是配置属性>常规>字符集>“使用Unicode字符集”
Source.cpp
#include <iostream>
#include <Windows.h>
#include "resource.h"
int main() {
auto hinst = ::GetModuleHandleW(NULL);
std::cout << hinst << std::endl;
auto hrsrc = ::FindResourceW(hinst, MAKEINTRESOURCE(IDTHING), RT_RCDATA);
std::cout << hrsrc << std::endl;
auto hglob = ::LoadResource(hinst, hrsrc);
std::cout << hglob << std::endl;
return 0;
}
resource.h
#define IDTHING 300
Resource.rc
#include "resource.h"
IDTHING RCDATA "C:\\Windows\\notepad.exe"
我完全避免了VS中所有自动生成的资源,而只是将它们写为纯文本文件。
如果您在调试器中运行,请在分配hglob
后停止并将其值放入内存窗口,我可以清楚地看到notepad.exe的PE标头。