Мне просто интересно, есть ли API в Windows для загрузки HICON
из массива байтов (буфер)? Предположим, что я загрузил файл *.ico
, и у меня есть содержимое этого файла в каком-то буфере. Я хочу иметь возможность создать HICON
из этого буфера.Загрузить HICON из буфера (* .ico файл)
Можно загрузить HICON
с *.ico
, который находится на жестком диске, поэтому я предполагаю, что должен быть такой же простой способ сделать это из буфера памяти?
До сих пор я нашел только 2 решения, но ни один из них не подходит для меня.
Первый involved ATL usage and GDI+ (Я использую Rust и у меня нет привязок к GDI +).
Второй был основан на использовании LookupIconIdFromDirectoryEx()
и CreateIconFromResourceEx()
. Сначала я позвонил LookupIconIdFromDirectoryEx()
, чтобы получить смещение для правильного значка, а затем попытался позвонить CreateIconFromResourceEx()
(и CreateIconFromResource()
), чтобы получить HICON, но во всех случаях я получаю значение NULL
, в результате возвращает 0
. Мое использование этих функций было основано на this article (я попытался передать не только 0
в качестве второго параметра, но и размер буфера массива, исключая смещение, но он все равно не работает).
Единственное оставшееся решение, которое я имею в виду, состоит в том, чтобы вручную проанализировать файл *.ico
, а затем извлечь из него PNG-изображения, а затем использовать описанный подход here, чтобы создать значок из изображения PNG. Но это похоже на обходное решение (Qt использует подобный подход, хотя, возможно, они не смогли найти другое решение). Существуют ли более простые методы (возможно, некоторые вызовы WinAPI), чтобы все было сделано?
UPD. Вот некоторый тестовый код, который я попробовал (у вас должен быть значок, чтобы запустить пример без сбоев).
#include <cstdio>
#include <cstdlib>
#include <Windows.h>
#pragma comment(lib, "User32.lib")
int main()
{
// Read the icon into the memory
FILE* f = fopen("icon.ico", "rb");
fseek(f, 0, SEEK_END);
long fsize = ftell(f);
fseek(f, 0, SEEK_SET);
char* data = (char*)malloc(fsize + 1);
fread(data, fsize, 1, f);
fclose(f);
static const int icon_size = 32;
int offset = LookupIconIdFromDirectoryEx((PBYTE)data, TRUE, icon_size, icon_size, LR_DEFAULTCOLOR);
if (offset != 0) {
HICON hicon = CreateIconFromResourceEx((PBYTE)data + offset, 0, TRUE, 0x30000, icon_size, icon_size, LR_DEFAULTCOLOR);
if (hicon != NULL) {
printf("SUCCESS");
return 0;
}
}
printf("FAIL %d", GetLastError());
return 1;
}
Похоже, что в вашем коде есть ошибка. Мы не можем вам помочь, если вы не предоставите [mcve]. – IInspectable
Исправьте свой код, а не сдадитесь –
@IInspectable, я не добавил его изначально, потому что он был в основном таким же, как и в статье, которую я связал. Но теперь я обновил описание и прикрепил туда исходный код. В моем случае он всегда печатает «FAIL 0». – ScienceSE