Sync to trunk head (r42241)
[reactos.git] / reactos / dll / win32 / user32 / windows / icon.c
1 /*
2 * ReactOS kernel
3 * Copyright (C) 1998, 1999, 2000, 2001 ReactOS Team
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 */
19 /* $Id$
20 *
21 * PROJECT: ReactOS user32.dll
22 * FILE: lib/user32/windows/icon.c
23 * PURPOSE: Icon
24 * PROGRAMMER: Casper S. Hornstrup (chorns@users.sourceforge.net)
25 * UPDATE HISTORY:
26 * 09-05-2001 CSH Created
27 */
28
29 /* INCLUDES ******************************************************************/
30
31 #include <user32.h>
32
33 #include <wine/debug.h>
34 WINE_DEFAULT_DEBUG_CHANNEL(user32);
35
36 /* FUNCTIONS *****************************************************************/
37
38
39 HICON
40 ICON_CreateIconFromData(HDC hDC, PVOID ImageData, ICONIMAGE* IconImage, int cxDesired, int cyDesired, int xHotspot, int yHotspot)
41 {
42 BYTE BitmapInfoBuffer[sizeof(BITMAPINFOHEADER) + 2 * sizeof(RGBQUAD)];
43 BITMAPINFO *bwBIH = (BITMAPINFO *)BitmapInfoBuffer;
44 ICONINFO IconInfo;
45
46 IconInfo.fIcon = TRUE;
47 IconInfo.xHotspot = xHotspot;
48 IconInfo.yHotspot = yHotspot;
49
50 /* Load the XOR bitmap */
51 IconInfo.hbmColor = CreateDIBitmap(hDC, &IconImage->icHeader, CBM_INIT,
52 ImageData, (BITMAPINFO*)IconImage,
53 DIB_RGB_COLORS);
54
55 /* Make ImageData point to the start of the AND image data. */
56 ImageData = ((PBYTE)ImageData) + (((IconImage->icHeader.biWidth *
57 IconImage->icHeader.biBitCount + 31) & ~31) >> 3) *
58 (IconImage->icHeader.biHeight );
59
60 /* Create a BITMAPINFO header for the monocrome part of the icon. */
61 bwBIH->bmiHeader.biBitCount = 1;
62 bwBIH->bmiHeader.biWidth = IconImage->icHeader.biWidth;
63 bwBIH->bmiHeader.biHeight = IconImage->icHeader.biHeight;
64 bwBIH->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
65 bwBIH->bmiHeader.biPlanes = 1;
66 bwBIH->bmiHeader.biSizeImage = 0;
67 bwBIH->bmiHeader.biCompression = BI_RGB;
68 bwBIH->bmiHeader.biClrImportant = 0;
69 bwBIH->bmiHeader.biClrUsed = 0;
70 bwBIH->bmiHeader.biXPelsPerMeter = 0;
71 bwBIH->bmiHeader.biYPelsPerMeter = 0;
72
73 bwBIH->bmiColors[0].rgbBlue = 0;
74 bwBIH->bmiColors[0].rgbGreen = 0;
75 bwBIH->bmiColors[0].rgbRed = 0;
76 bwBIH->bmiColors[0].rgbReserved = 0;
77
78 bwBIH->bmiColors[1].rgbBlue = 0xff;
79 bwBIH->bmiColors[1].rgbGreen = 0xff;
80 bwBIH->bmiColors[1].rgbRed = 0xff;
81 bwBIH->bmiColors[1].rgbReserved = 0;
82
83 /* Load the AND bitmap. */
84 IconInfo.hbmMask = CreateDIBitmap(hDC, &bwBIH->bmiHeader, 0,
85 ImageData, bwBIH, DIB_RGB_COLORS);
86
87 SetDIBits(hDC, IconInfo.hbmMask, 0, IconImage->icHeader.biHeight,
88 ImageData, bwBIH, DIB_RGB_COLORS);
89
90 /* Create the icon based on everything we have so far */
91 return NtUserCreateCursorIconHandle(&IconInfo, FALSE);
92 }
93
94 HICON
95 ICON_CreateCursorFromData(HDC hDC, PVOID ImageData, ICONIMAGE* IconImage, int cxDesired, int cyDesired, int xHotspot, int yHotspot)
96 {
97 BYTE BitmapInfoBuffer[sizeof(BITMAPINFOHEADER) + 2 * sizeof(RGBQUAD)];
98 BITMAPINFO *bwBIH = (BITMAPINFO *)BitmapInfoBuffer;
99 BITMAPINFO *orgBIH = (BITMAPINFO *)IconImage;
100 ICONINFO IconInfo;
101 PVOID XORImageData = ImageData;
102
103 IconInfo.fIcon = FALSE;
104 IconInfo.xHotspot = xHotspot;
105 IconInfo.yHotspot = yHotspot;
106
107 /* Create a BITMAPINFO header for the monochrome part of the icon */
108 bwBIH->bmiHeader.biBitCount = 1;
109 bwBIH->bmiHeader.biWidth = IconImage->icHeader.biWidth;
110 bwBIH->bmiHeader.biHeight = IconImage->icHeader.biHeight;
111 bwBIH->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
112 bwBIH->bmiHeader.biPlanes = 1;
113 bwBIH->bmiHeader.biSizeImage = 0;
114 bwBIH->bmiHeader.biCompression = BI_RGB;
115 bwBIH->bmiHeader.biClrImportant = 0;
116 bwBIH->bmiHeader.biClrUsed = 0;
117 bwBIH->bmiHeader.biXPelsPerMeter = 0;
118 bwBIH->bmiHeader.biYPelsPerMeter = 0;
119
120 bwBIH->bmiColors[0].rgbBlue = 0;
121 bwBIH->bmiColors[0].rgbGreen = 0;
122 bwBIH->bmiColors[0].rgbRed = 0;
123 bwBIH->bmiColors[0].rgbReserved = 0;
124
125 bwBIH->bmiColors[1].rgbBlue = 0xff;
126 bwBIH->bmiColors[1].rgbGreen = 0xff;
127 bwBIH->bmiColors[1].rgbRed = 0xff;
128 bwBIH->bmiColors[1].rgbReserved = 0;
129
130 /* Load the AND bitmap */
131 IconInfo.hbmMask = CreateDIBitmap(hDC, &bwBIH->bmiHeader, 0,
132 XORImageData, bwBIH, DIB_RGB_COLORS);
133 if (IconInfo.hbmMask)
134 {
135 SetDIBits(hDC, IconInfo.hbmMask, 0, IconImage->icHeader.biHeight,
136 XORImageData, orgBIH, DIB_RGB_COLORS);
137 }
138
139 if (IconImage->icHeader.biBitCount == 1)
140 {
141 IconInfo.hbmColor = (HBITMAP)0;
142 }
143 else
144 {
145 /* Create the color part of the icon */
146 IconInfo.hbmColor = CreateDIBitmap(hDC, &IconImage->icHeader, 0,
147 XORImageData, orgBIH, DIB_RGB_COLORS);
148 if (IconInfo.hbmColor)
149 {
150 SetDIBits(hDC, IconInfo.hbmColor, 0, IconImage->icHeader.biHeight,
151 XORImageData, orgBIH, DIB_RGB_COLORS);
152 }
153 }
154
155 /* Create the icon based on everything we have so far */
156 return NtUserCreateCursorIconHandle(&IconInfo, FALSE);
157 }
158
159
160 /*
161 * @implemented
162 */
163 HICON
164 WINAPI
165 CopyIcon(HICON hIcon)
166 {
167 HICON hRetIcon = NULL;
168 ICONINFO IconInfo;
169
170 if(GetIconInfo(hIcon, &IconInfo))
171 {
172 hRetIcon = CreateIconIndirect(&IconInfo);
173 DeleteObject(IconInfo.hbmColor);
174 DeleteObject(IconInfo.hbmMask);
175 }
176
177 return hRetIcon;
178 }
179
180
181 /*
182 * @implemented
183 */
184 HICON
185 WINAPI
186 CreateIcon(
187 HINSTANCE hInstance,
188 int nWidth,
189 int nHeight,
190 BYTE cPlanes,
191 BYTE cBitsPixel,
192 CONST BYTE *ANDbits,
193 CONST BYTE *XORbits)
194 {
195 ICONINFO IconInfo;
196
197 IconInfo.fIcon = TRUE;
198
199 if (cBitsPixel == 1)
200 {
201 nHeight <<= 1;
202 }
203 IconInfo.hbmMask = CreateBitmap(nWidth, nHeight, 1, 1, ANDbits);
204 if(!IconInfo.hbmMask)
205 {
206 return (HICON)0;
207 }
208
209 if (cBitsPixel == 1)
210 {
211 IconInfo.hbmColor = (HBITMAP)0;
212 }
213 else
214 {
215 IconInfo.hbmColor = CreateBitmap(nWidth, nHeight, cPlanes, cBitsPixel, XORbits);
216 if(!IconInfo.hbmColor)
217 {
218 DeleteObject(IconInfo.hbmMask);
219 return (HICON)0;
220 }
221 }
222
223 return NtUserCreateCursorIconHandle(&IconInfo, FALSE);
224 }
225
226
227 /*
228 * @implemented
229 */
230 HICON
231 WINAPI
232 CreateIconFromResource(
233 PBYTE presbits,
234 DWORD dwResSize,
235 BOOL fIcon,
236 DWORD dwVer)
237 {
238 return CreateIconFromResourceEx(presbits, dwResSize, fIcon, dwVer, 0, 0, LR_DEFAULTSIZE|LR_SHARED );
239 }
240
241
242 /*
243 * @implemented
244 */
245 HICON
246 WINAPI
247 CreateIconFromResourceEx(
248 PBYTE pbIconBits,
249 DWORD cbIconBits,
250 BOOL fIcon,
251 DWORD dwVersion,
252 int cxDesired,
253 int cyDesired,
254 UINT uFlags)
255 {
256 ICONIMAGE* SafeIconImage;
257 HICON hIcon;
258 ULONG HeaderSize;
259 ULONG ColourCount;
260 PVOID Data;
261 HDC hScreenDc;
262 WORD wXHotspot;
263 WORD wYHotspot;
264
265 /*
266 FIXME - does win support LR_SHARED? According to msdn it does but we don't
267 have useful information to identify the icon
268 if (uFlags & LR_SHARED)
269 {
270 DbgPrint("FIXME: need LR_SHARED support in CreateIconFromResourceEx()\n");
271 }
272 */
273
274 TRACE("dwVersion, cxDesired, cyDesired are all ignored in this implementation!\n");
275
276 if (! fIcon)
277 {
278 wXHotspot = *(WORD*)pbIconBits;
279 pbIconBits += sizeof(WORD);
280 wYHotspot = *(WORD*)pbIconBits;
281 pbIconBits += sizeof(WORD);
282 cbIconBits -= 2 * sizeof(WORD);
283 }
284 else
285 {
286 wXHotspot = cxDesired / 2;
287 wYHotspot = cyDesired / 2;
288 }
289
290 /* get an safe copy of the icon data */
291 SafeIconImage = RtlAllocateHeap(GetProcessHeap(), 0, cbIconBits);
292 if (SafeIconImage == NULL)
293 {
294 return NULL;
295 }
296 memcpy(SafeIconImage, pbIconBits, cbIconBits);
297
298 /* take into acount the original height was for both the AND and XOR images */
299 if(fIcon)
300 SafeIconImage->icHeader.biHeight /= 2;
301
302 if (SafeIconImage->icHeader.biSize == sizeof(BITMAPCOREHEADER))
303 {
304 BITMAPCOREHEADER* Core = (BITMAPCOREHEADER*)SafeIconImage;
305 ColourCount = (Core->bcBitCount <= 8) ? (1 << Core->bcBitCount) : 0;
306 HeaderSize = sizeof(BITMAPCOREHEADER) + ColourCount * sizeof(RGBTRIPLE);
307 }
308 else
309 {
310 ColourCount = (SafeIconImage->icHeader.biBitCount <= 8) ?
311 (1 << SafeIconImage->icHeader.biBitCount) : 0;
312 HeaderSize = sizeof(BITMAPINFOHEADER) + ColourCount * sizeof(RGBQUAD);
313 }
314
315 /* make data point to the start of the XOR image data */
316 Data = (PBYTE)SafeIconImage + HeaderSize;
317
318 /* get a handle to the screen dc, the icon we create is going to be compatable with this */
319 // FIXME!!! This is a victim of the Win32k Initialization BUG!!!!!
320 //hScreenDc = CreateDCW(NULL, NULL, NULL, NULL);
321 hScreenDc = CreateCompatibleDC(NULL);
322 if (hScreenDc == NULL)
323 {
324 RtlFreeHeap(GetProcessHeap(), 0, SafeIconImage);
325 return(NULL);
326 }
327
328 if(fIcon)
329 hIcon = ICON_CreateIconFromData(hScreenDc, Data, SafeIconImage, cxDesired, cyDesired, wXHotspot, wYHotspot);
330 else
331 hIcon = ICON_CreateCursorFromData(hScreenDc, Data, SafeIconImage, cxDesired, cyDesired, wXHotspot, wYHotspot);
332 RtlFreeHeap(GetProcessHeap(), 0, SafeIconImage);
333 DeleteDC(hScreenDc);
334
335 return hIcon;
336 }
337
338
339 /*
340 * @implemented
341 */
342 HICON
343 WINAPI
344 CreateIconIndirect(PICONINFO IconInfo)
345 {
346 BITMAP ColorBitmap;
347 BITMAP MaskBitmap;
348 HBITMAP hbmTemp;
349
350 if(!IconInfo)
351 {
352 SetLastError(ERROR_INVALID_PARAMETER);
353 return (HICON)0;
354 }
355
356 if(!GetObjectW(IconInfo->hbmMask, sizeof(BITMAP), &MaskBitmap))
357 {
358 return (HICON)0;
359 }
360
361 /* Try to get color bitmap */
362 if (GetObjectW(IconInfo->hbmColor, sizeof(BITMAP), &ColorBitmap))
363 {
364 /* Compare size of color and mask bitmap*/
365 if (ColorBitmap.bmWidth != MaskBitmap.bmWidth ||
366 ColorBitmap.bmHeight != MaskBitmap.bmHeight)
367 {
368 ERR("Color and mask size are different!");
369 SetLastError(ERROR_INVALID_PARAMETER);
370 return (HICON)0;
371 }
372 /* Check if color and mask are switched and switch them back */
373 if (MaskBitmap.bmBitsPixel != 1 && ColorBitmap.bmBitsPixel == 1)
374 {
375 hbmTemp = IconInfo->hbmMask;
376 IconInfo->hbmMask = IconInfo->hbmColor;
377 IconInfo->hbmColor = hbmTemp;
378 }
379 }
380 return (HICON)NtUserCreateCursorIconHandle(IconInfo, TRUE);
381 }
382
383
384 /*
385 * @implemented
386 */
387 BOOL
388 WINAPI
389 DestroyIcon(
390 HICON hIcon)
391 {
392 return (BOOL)NtUserDestroyCursor((HANDLE)hIcon, 0);
393 }
394
395
396 /*
397 * @implemented
398 */
399 BOOL
400 WINAPI
401 DrawIcon(
402 HDC hDC,
403 int X,
404 int Y,
405 HICON hIcon)
406 {
407 return DrawIconEx(hDC, X, Y, hIcon, 0, 0, 0, NULL, DI_NORMAL | DI_DEFAULTSIZE);
408 }
409
410 /*
411 * @implemented
412 */
413 BOOL
414 WINAPI
415 DrawIconEx(
416 HDC hdc,
417 int xLeft,
418 int yTop,
419 HICON hIcon,
420 int cxWidth,
421 int cyWidth,
422 UINT istepIfAniCur,
423 HBRUSH hbrFlickerFreeDraw,
424 UINT diFlags)
425 {
426 return (BOOL)NtUserDrawIconEx(hdc, xLeft, yTop, hIcon, cxWidth, cyWidth,
427 istepIfAniCur, hbrFlickerFreeDraw, diFlags,
428 0, 0);
429 }
430
431
432 /*
433 * @implemented
434 */
435 BOOL
436 WINAPI
437 GetIconInfo(
438 HICON hIcon,
439 PICONINFO IconInfo)
440 {
441 return NtUserGetIconInfo((HANDLE)hIcon, IconInfo, 0, 0, 0, 0);
442 }
443
444
445 /*
446 * @implemented
447 */
448 HICON
449 WINAPI
450 LoadIconA(
451 HINSTANCE hInstance,
452 LPCSTR lpIconName)
453 {
454 return(LoadImageA(hInstance, lpIconName, IMAGE_ICON, 0, 0, LR_SHARED | LR_DEFAULTSIZE));
455 }
456
457
458 /*
459 * @implemented
460 */
461 HICON
462 WINAPI
463 LoadIconW(
464 HINSTANCE hInstance,
465 LPCWSTR lpIconName)
466 {
467 return(LoadImageW(hInstance, lpIconName, IMAGE_ICON, 0, 0, LR_SHARED | LR_DEFAULTSIZE));
468 }
469
470
471 /*
472 * @implemented
473 */
474 int
475 WINAPI
476 LookupIconIdFromDirectory(
477 PBYTE presbits,
478 BOOL fIcon)
479 {
480 return LookupIconIdFromDirectoryEx(presbits,
481 fIcon,
482 fIcon ? GetSystemMetrics(SM_CXICON) : GetSystemMetrics(SM_CXCURSOR),
483 fIcon ? GetSystemMetrics(SM_CYICON) : GetSystemMetrics(SM_CYCURSOR),
484 LR_DEFAULTCOLOR);
485 }
486
487
488
489
490
491 /*
492 * The following macro function accounts for the irregularities of
493 * accessing cursor and icon resources in files and resource entries.
494 */
495 typedef BOOL
496 (*fnGetCIEntry)(LPVOID dir, int n, int *width, int *height, int *bits );
497
498 /**********************************************************************
499 * CURSORICON_FindBestIcon
500 *
501 * Find the icon closest to the requested size and number of colors.
502 */
503 static int
504 CURSORICON_FindBestIcon(LPVOID dir,
505 fnGetCIEntry get_entry,
506 int Width,
507 int Height,
508 int ColorBits)
509 {
510 int i, cx, cy, Bits, BestBits = 0, BestEntry = -1;
511 UINT iTotalDiff, iXDiff=0, iYDiff=0, iColorDiff;
512 UINT iTempXDiff, iTempYDiff, iTempColorDiff;
513
514 /* Find Best Fit */
515 iTotalDiff = 0xFFFFFFFF;
516 iColorDiff = 0xFFFFFFFF;
517 for (i = 0; get_entry(dir, i, &cx, &cy, &Bits); i++ )
518 {
519 iTempXDiff = abs(Width - cx);
520 iTempYDiff = abs(Height - cy);
521
522 if(iTotalDiff > (iTempXDiff + iTempYDiff))
523 {
524 iXDiff = iTempXDiff;
525 iYDiff = iTempYDiff;
526 iTotalDiff = iXDiff + iYDiff;
527 }
528 }
529
530 /* Find Best Colors for Best Fit */
531 for (i = 0; get_entry(dir, i, &cx, &cy, &Bits); i++ )
532 {
533 if(abs(Width - cx) == iXDiff && abs(Height - cy) == iYDiff)
534 {
535 iTempColorDiff = abs(ColorBits - Bits);
536 if(iColorDiff > iTempColorDiff)
537 {
538 BestEntry = i;
539 BestBits = Bits;
540 iColorDiff = iTempColorDiff;
541 }
542 }
543 }
544
545 TRACE("Best Icon: ResId: %d, bits : %d\n", BestEntry, BestBits);
546
547 return BestEntry;
548 }
549
550
551
552 /**********************************************************************
553 * CURSORICON_FindBestCursor
554 *
555 * Find the cursor closest to the requested size.
556 * FIXME: parameter 'color' ignored and entries with more than 1 bpp
557 * ignored too
558 */
559 static int
560 CURSORICON_FindBestCursor(LPVOID dir,
561 fnGetCIEntry get_entry,
562 int Width,
563 int Height,
564 int ColorBits)
565 {
566 int i, cx, cy, Bits, BestBits = 0, BestEntry = -1;
567 UINT iTotalDiff, iXDiff=0, iYDiff=0, iColorDiff;
568 UINT iTempXDiff, iTempYDiff, iTempColorDiff;
569
570 /* Find Best Fit */
571 iTotalDiff = 0xFFFFFFFF;
572 iColorDiff = 0xFFFFFFFF;
573 for (i = 0; get_entry(dir, i, &cx, &cy, &Bits); i++ )
574 {
575 iTempXDiff = abs(Width - cx);
576 iTempYDiff = abs(Height - cy);
577
578 if(iTotalDiff > (iTempXDiff + iTempYDiff))
579 {
580 iXDiff = iTempXDiff;
581 iYDiff = iTempYDiff;
582 iTotalDiff = iXDiff + iYDiff;
583 }
584 }
585
586 /* Find Best Colors for Best Fit */
587 for (i = 0; get_entry(dir, i, &cx, &cy, &Bits); i++ )
588 {
589 if(abs(Width - cx) == iXDiff && abs(Height - cy) == iYDiff)
590 {
591 iTempColorDiff = abs(ColorBits - Bits);
592 if(iColorDiff > iTempColorDiff)
593 {
594 BestEntry = i;
595 BestBits = Bits;
596 iColorDiff = iTempColorDiff;
597 }
598 }
599 }
600
601 TRACE("Best Cursor: ResId: %d, bits : %d\n", BestEntry, BestBits);
602
603 return BestEntry;
604 }
605
606
607 static BOOL
608 CURSORICON_GetResIconEntry(LPVOID dir,
609 int n,
610 int *Width,
611 int *Height,
612 int *Bits)
613 {
614 GRPCURSORICONDIR *ResDir = dir;
615 ICONRESDIR *Icon;
616
617 if (ResDir->idCount <= n)
618 return FALSE;
619
620 Icon = &ResDir->idEntries[n].ResInfo.icon;
621 *Width = Icon->bWidth;
622 *Height = Icon->bHeight;
623 *Bits = ResDir->idEntries[n].wBitCount;
624 return TRUE;
625 }
626
627 static BOOL
628 CURSORICON_GetResCursorEntry(LPVOID dir,
629 int n,
630 int *Width,
631 int *Height,
632 int *Bits)
633 {
634 GRPCURSORICONDIR *ResDir = dir;
635 CURSORRESDIR *Cursor;
636
637 if (ResDir->idCount <= n)
638 return FALSE;
639
640 Cursor = &ResDir->idEntries[n].ResInfo.cursor;
641 *Width = Cursor->wWidth;
642 *Height = Cursor->wHeight;
643 *Bits = ResDir->idEntries[n].wBitCount;
644 return TRUE;
645 }
646
647 static GRPCURSORICONDIRENTRY *
648 CURSORICON_FindBestIconRes(GRPCURSORICONDIR * dir,
649 int Width,
650 int Height,
651 int ColorBits)
652 {
653 int n;
654 n = CURSORICON_FindBestIcon(dir,
655 CURSORICON_GetResIconEntry,
656 Width,
657 Height,
658 ColorBits);
659 if (n < 0)
660 return NULL;
661
662 return &dir->idEntries[n];
663 }
664
665 static GRPCURSORICONDIRENTRY *
666 CURSORICON_FindBestCursorRes(GRPCURSORICONDIR *dir,
667 int Width,
668 int Height,
669 int ColorBits)
670 {
671 int n;
672 n = CURSORICON_FindBestCursor(dir,
673 CURSORICON_GetResCursorEntry,
674 Width,
675 Height,
676 ColorBits);
677 if (n < 0)
678 return NULL;
679
680 return &dir->idEntries[n];
681 }
682
683
684 INT WINAPI
685 LookupIconIdFromDirectoryEx(PBYTE xdir,
686 BOOL bIcon,
687 INT width,
688 INT height,
689 UINT cFlag)
690 {
691 GRPCURSORICONDIR *dir = (GRPCURSORICONDIR*)xdir;
692 UINT retVal = 0;
693
694 GetConnected();
695
696 if(dir && !dir->idReserved && (IMAGE_ICON == dir->idType || IMAGE_CURSOR == dir->idType))
697 {
698 GRPCURSORICONDIRENTRY *entry = NULL;
699 int ColorBits;
700
701 if (cFlag & LR_MONOCHROME)
702 {
703 ColorBits = 1;
704 }
705 else if (cFlag & LR_VGACOLOR)
706 {
707 ColorBits = 4;
708 }
709 else
710 {
711 ColorBits = g_psi->BitsPixel;
712 }
713
714 if(bIcon)
715 entry = CURSORICON_FindBestIconRes(dir, width, height, ColorBits);
716 else
717 entry = CURSORICON_FindBestCursorRes(dir, width, height, 1);
718
719 if (entry)
720 retVal = entry->nID;
721 }
722 else
723 WARN("%s() : Invalid resource directory\n", __FUNCTION__);
724
725 return retVal;
726 }