This is the mail archive of the
cygwin-xfree
mailing list for the Cygwin XFree86 project.
Re: Icons
- From: "Colin Harrison" <colin dot harrison at virgin dot net>
- To: <cygwin-xfree at cygwin dot com>
- Date: Tue, 30 Aug 2005 02:03:18 +0100
- Subject: Re: Icons
- Reply-to: cygwin-xfree at cygwin dot com
Hi,
Here's my rough solution (to iconSize conversion problem):-
--- save_winmultiwindowicons.c 2005-08-30 01:57:27.000000000 +0100
+++ winmultiwindowicons.c 2005-08-30 01:45:58.000000000 +0100
@@ -54,6 +54,7 @@
winScaleXBitmapToWindows (int iconSize, int effBPP,
PixmapPtr pixmap, unsigned char *image);
+HICON Convert32x32IconTo16x16(HICON h32x32Icon);
/*
* Scale an X icon bitmap into a Windoze icon bitmap
@@ -278,13 +279,18 @@
ICONINFO ii;
WinXWMHints hints;
HICON hIcon;
+ BOOL convert=FALSE;
winMultiWindowGetWMHints (pWin, &hints);
if (!hints.icon_pixmap) return NULL;
- iconPtr = LookupIDByType (hints.icon_pixmap, RT_PIXMAP);
+ iconPtr = (PixmapPtr) LookupIDByType (hints.icon_pixmap, RT_PIXMAP);
if (!iconPtr) return NULL;
+
+ if (iconSize == 16) convert = TRUE;
+
+ iconSize = 32;
hDC = GetDC (GetDesktopWindow ());
planes = GetDeviceCaps (hDC, PLANES);
@@ -311,7 +317,7 @@
memset (mask, 0, maskStride * iconSize);
winScaleXBitmapToWindows (iconSize, effBPP, iconPtr, image);
- maskPtr = LookupIDByType (hints.icon_mask, RT_PIXMAP);
+ maskPtr = (PixmapPtr) LookupIDByType (hints.icon_mask, RT_PIXMAP);
if (maskPtr)
{
@@ -330,6 +336,14 @@
else
dst++;
}
+ else
+ {
+ /* Free X mask and bitmap */
+ free (mask);
+ free (image);
+ free (imageMask);
+ return NULL;
+ }
ii.fIcon = TRUE;
ii.xHotspot = 0; /* ignored */
@@ -344,6 +358,8 @@
/* Merge Win32 mask and bitmap into icon */
hIcon = CreateIconIndirect (&ii);
+ if (convert) hIcon=Convert32x32IconTo16x16(hIcon);
+
/* Release Win32 mask and bitmap */
DeleteObject (ii.hbmMask);
DeleteObject (ii.hbmColor);
@@ -369,7 +385,7 @@
WindowPtr pWin;
HICON hIcon, hiconOld;
- pWin = LookupIDByType (id, RT_WINDOW);
+ pWin = (WindowPtr) LookupIDByType (id, RT_WINDOW);
hIcon = (HICON)winOverrideIcon ((unsigned long)pWin);
if (!hIcon)
@@ -476,3 +492,75 @@
DestroyIcon (hIcon);
}
#endif
+
+
+HICON Convert32x32IconTo16x16(HICON h32x32Icon)
+{
+ HDC hMainDC, hMemDC1, hMemDC2;
+ HICON h16x16Icon;
+ BITMAP bmp;
+ HBITMAP hOldBmp1, hOldBmp2;
+ ICONINFO IconInfo32x32, IconInfo16x16;
+
+ GetIconInfo(h32x32Icon, &IconInfo32x32);
+
+ hMainDC = GetDC(GetDesktopWindow ());
+ hMemDC1 = CreateCompatibleDC(hMainDC);
+ hMemDC2 = CreateCompatibleDC(hMainDC);
+
+ GetObject(IconInfo32x32.hbmColor, sizeof(BITMAP), &bmp);
+
+ IconInfo16x16.hbmColor = CreateBitmap( 16, 16,
+ bmp.bmPlanes,
+ bmp.bmBitsPixel,
+ NULL);
+
+ hOldBmp1 = (HBITMAP) SelectObject( hMemDC1,
+ IconInfo32x32.hbmColor);
+ hOldBmp2 = (HBITMAP) SelectObject( hMemDC2,
+ IconInfo16x16.hbmColor);
+
+ StretchBlt(hMemDC2,
+ 0, 0,
+ 16, 16,
+ hMemDC1,
+ 0, 0,
+ 32, 32,
+ SRCCOPY
+ );
+
+ GetObject(IconInfo32x32.hbmMask, sizeof(BITMAP), &bmp);
+
+ IconInfo16x16.hbmMask = CreateBitmap( 16, 16,
+ bmp.bmPlanes,
+ bmp.bmBitsPixel,
+ NULL);
+
+ SelectObject(hMemDC1, IconInfo32x32.hbmMask);
+ SelectObject(hMemDC2, IconInfo16x16.hbmMask);
+
+ StretchBlt(hMemDC2,
+ 0, 0,
+ 16, 16,
+ hMemDC1,
+ 0, 0,
+ 32, 32,
+ SRCCOPY
+ );
+
+ SelectObject(hMemDC1, hOldBmp1);
+ SelectObject(hMemDC2, hOldBmp2);
+
+ IconInfo16x16.fIcon = TRUE;
+ h16x16Icon = CreateIconIndirect(&IconInfo16x16);
+
+ DeleteObject(IconInfo32x32.hbmColor);
+ DeleteObject(IconInfo16x16.hbmColor);
+ DeleteObject(IconInfo32x32.hbmMask);
+ DeleteObject(IconInfo16x16.hbmMask);
+ DeleteDC(hMemDC1);
+ DeleteDC(hMemDC2);
+ ReleaseDC(GetDesktopWindow (), hMainDC);
+
+ return h16x16Icon;
+}
Includes some safety casts and a null mask catcher (I have had black square
icons from dodgy clients, this patch forces the default X).
Colin Harrison
--
Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple
Problem reports: http://cygwin.com/problems.html
Documentation: http://x.cygwin.com/docs/
FAQ: http://x.cygwin.com/docs/faq/