Grigoriy |
Отправлено: 25.07.2006, 05:47 |
|
Мастер участка
Группа: Участник
Сообщений: 381
|
Есть в АПИ функция
CODE |
WINSHELLAPI DWORD WINAPI SHGetFileInfo(
LPCTSTR pszPath,
DWORD dwFileAttributes,
SHFILEINFO FAR *psfi,
UINT cbFileInfo,
UINT uFlags
);
|
pszPath — полное имя файла;
dwFileAttributes — массив атрибутов файла (учитывается при включенном флаге SHGFI_USEFILEATTRIBUTES);
psfi — адрес структуры SHFILEINFO, которую заполнит в случае успеха функция;
cbFileInfo — размер SHFILEINFO;
uFlags — флаги, указывающие на тип извлекаемой информации.
CODE |
typedef struct _SHFILEINFO { // shfi
HICON hIcon;
int iIcon;
DWORD dwAttributes;
char szDisplayName[MAX_PATH];
char szTypeName[80];
} SHFILEINFO;
|
Здесь hIcon — дескриптор возвращаемой иконки, а
iIcon — индекс этой же иконки в системном хранилище изображений
Дело в том, что я хочу рисовать иконки для файлов.
Я знаю как это сделать функцией DrawIconEx.
Функция SHGetFileInfo выделяет память для иконки файла и возвращает отдельный ХЕНДЛ иконки. Затем иконку можно нарисовать в нужном масштабе и в нужной позиции функцией DrawIconEx.
Но важно то, что при этом увеличивается количество ХЕНДЛов и оно может стать огромным, если в каталоге очень много файлов.
И при очень большом количестве иконок процесс копирования иконок затягивается, а этого не хотелось бы.
Кроме того, я обнаружил, что если очень много иконок копирует система и для каждой из них выдает отдельный HANDLE, то наступит такой момент, когда система просто откажет в выделении ХЕНДЛов иконок для программы и программа заглючит. Я не буду приводить здесь кода моей программы, поскольку он уже просто для меня лично огромный. Надеюсь, что будет понятно и так.
У меня вопрос.
Можно ли использовать возвращаемый индекс иконки в системном хранилище изобжений для рисования иконки и как в таком случае нарисовать ее ?
Заранее спасибо, если мне хорошо ответят.
|
|
Kuks |
Отправлено: 25.07.2006, 08:33 |
|
Станционный диспетчер
Группа: Участник
Сообщений: 108
|
CODE | SHFILEINFO shfi;
TIcon *Icon = new TIcon;
SHGetFileInfo(OpenDialog->FileName.c_str(),FILE_ATTRIBUTE_NORMAL,&shfi, sizeof(shfi),SHGFI_ICON|SHGFI_USEFILEATTRIBUTES);
Icon->Handle = shfi.hIcon; |
Так не пойдет?
|
|
Grigoriy |
Отправлено: 25.07.2006, 09:09 |
|
Мастер участка
Группа: Участник
Сообщений: 381
|
В таком случае вообще не нужно создавать в своей программе
CODE |
TIcon *Icon = new TIcon;
|
Достаточно просто
потому что объект Иконку Windows создает сама.
Да я и использую это сейчас.
И я же об этом сообщил.
Этот метод имеет недостаток в том, что создаются копии иконок системой и это занимает время и есть некий предел количества дескрипторов иконок, выделяемых программе.
А мне нужно использовать
shfi.iIcon.
В общем есть такая функция
CODE |
BOOL ImageList_DrawEx(
HIMAGELIST himl, // handle to the image list
int i, // index of the image to draw
HDC hdcDst, // handle to the destination device context
int x, // x-coordinate to draw at
int y, // y-coordinate to draw at
int dx, // width of image
int dy, // height of image
COLORREF rgbBk, // background color of image
COLORREF rgbFg, // foreground color of image
UINT fStyle // drawing style
);
|
Только я не знаю HANDLE системного ImageList
Отредактировано Grigoriy — 25/07/2006, 09:41
|
|
Grigoriy |
Отправлено: 25.07.2006, 09:55 |
|
Мастер участка
Группа: Участник
Сообщений: 381
|
Нашел решение.
Сама функция SHGetFileInfo возвращает дескриптор системного хранилища изображений.
|
|
Grigoriy |
Отправлено: 26.07.2006, 07:28 |
|
Мастер участка
Группа: Участник
Сообщений: 381
|
Только не масштабирует чего-то
функция
ImageList_DrawEx
некоторые иконки, в часности
иконки от исполняемых файлов. В этих иконках изображение получается из ресурса самого исполняемого файла.
|
|
Grigoriy |
Отправлено: 30.07.2006, 13:47 |
|
Мастер участка
Группа: Участник
Сообщений: 381
|
Для каких расширений файлов могут быть для разных файлов разные иконки ?
Вот например, для всех EXE-файлов иконки разные, потому что изображение берется из ресурса исполняемого файла. Ещё для ICO иконки разные. Для большинства же файлов иконки одинаковые.
Мне это нужно для правильного отбражения иконок для файлов. Для ускорения вывода иконок я объявил так называемый список
CODE |
TStringList* IconExtList;
/*Список расширений файлов и соответствующих им номеров иконок в системном ImageList*/
|
Сначала программа проверяет, есть ли строка с расширением файла в этом списке. Если есть, то программа выбирает номер иконки по (int)IconExtList->Objects[indexico]
Если нет, то добавляет строку и номер иконки, возвращенный функцией SHGetFileInfo
Ускорение действительно работает.
|
|
|