Commit 9ce8382e authored by Susan Farley's avatar Susan Farley Committed by Alexandre Julliard

Set and retrieve the window icon that is drawn under managed mode

(based on the work of Andrew Lewycky for Corel).
parent 9700b7fa
......@@ -97,6 +97,7 @@ typedef struct tagWND
#define HAK_BITGRAVITY 1
#define HAK_ACCEPTFOCUS 2
#define HAK_ICONICSTATE 3
#define HAK_ICONS 4
/* Bit Gravity */
......@@ -195,6 +196,8 @@ extern BOOL WIN_IsWindowDrawable(WND*, BOOL );
extern WND** WIN_BuildWinArray( WND *wndPtr, UINT bwa, UINT* pnum );
extern void WIN_ReleaseWinArray(WND **wndArray);
extern HICON16 NC_IconForWindow( WND *wndPtr );
extern HWND CARET_GetHwnd(void);
extern void CARET_GetRect(LPRECT lprc); /* windows/caret.c */
......
......@@ -406,6 +406,7 @@ extern struct tagWND_DRIVER X11DRV_WND_Driver;
typedef struct _X11DRV_WND_DATA {
Window window;
HBITMAP hWMIconBitmap;
HBITMAP hWMIconMask;
int bit_gravity;
} X11DRV_WND_DATA;
......
......@@ -463,21 +463,27 @@ static LRESULT DEFWND_DefWinProc( WND *wndPtr, UINT msg, WPARAM wParam,
return 1;
case WM_SETICON:
case WM_GETICON:
{
LRESULT result = 0;
int index = GCL_HICON;
{
int index = (wParam != ICON_SMALL) ? GCL_HICON : GCL_HICONSM;
HICON16 hOldIcon = GetClassLongA(wndPtr->hwndSelf, index);
SetClassLongA(wndPtr->hwndSelf, index, lParam);
if (wParam == ICON_SMALL)
index = GCL_HICONSM;
SetWindowPos(wndPtr->hwndSelf, 0, 0, 0, 0, 0, SWP_FRAMECHANGED
| SWP_NOSIZE | SWP_NOMOVE | SWP_NOACTIVATE
| SWP_NOZORDER);
result = GetClassLongA(wndPtr->hwndSelf, index);
if( wndPtr->flags & WIN_NATIVE )
wndPtr->pDriver->pSetHostAttr(wndPtr, HAK_ICONS, 0);
if (msg == WM_SETICON)
SetClassLongA(wndPtr->hwndSelf, index, lParam);
return hOldIcon;
}
case WM_GETICON:
{
int index = (wParam != ICON_SMALL) ? GCL_HICON : GCL_HICONSM;
return GetClassLongA(wndPtr->hwndSelf, index);
}
return result;
}
case WM_HELP:
SendMessageA( wndPtr->parent->hwndSelf, msg, wParam, lParam );
break;
......
......@@ -376,11 +376,11 @@ DrawCaptionTempA (HWND hwnd, HDC hdc, const RECT *rect, HFONT hFont,
GetSystemMetrics(SM_CYSMICON), 0, 0, DI_NORMAL);
}
else {
HICON hAppIcon = (HICON) GetClassLongA(hwnd, GCL_HICONSM);
if(!hAppIcon) hAppIcon = (HICON) GetClassLongA(hwnd, GCL_HICON);
WND* wndPtr = WIN_FindWndPtr(hwnd);
HICON hAppIcon = (HICON) NC_IconForWindow(wndPtr);
DrawIconEx (hdc, pt.x, pt.y, hAppIcon, GetSystemMetrics(SM_CXSMICON),
GetSystemMetrics(SM_CYSMICON), 0, 0, DI_NORMAL);
WIN_ReleaseWndPtr(wndPtr);
}
rc.left += (rc.bottom - rc.top);
......@@ -870,14 +870,7 @@ NC_DoNCHitTest95 (WND *wndPtr, POINT16 pt )
/* Check system menu */
if(wndPtr->dwStyle & WS_SYSMENU)
{
/* Check if there is an user icon */
HICON hIcon = (HICON) GetClassLongA(wndPtr->hwndSelf, GCL_HICONSM);
if(!hIcon) hIcon = (HICON) GetClassLongA(wndPtr->hwndSelf, GCL_HICON);
/* If there is an icon associated with the window OR */
/* If there is no hIcon specified and this is not a modal dialog, */
/* there is a system menu icon. */
if((hIcon != 0) || (!(wndPtr->dwStyle & DS_MODALFRAME)))
if (NC_IconForWindow(wndPtr))
rect.left += GetSystemMetrics(SM_CYCAPTION) - 1;
}
if (pt.x < rect.left) return HTSYSMENU;
......@@ -1073,14 +1066,7 @@ NC_DrawSysButton95 (HWND hwnd, HDC hdc, BOOL down)
NC_GetInsideRect95( hwnd, &rect );
hIcon = (HICON) GetClassLongA(wndPtr->hwndSelf, GCL_HICONSM);
if(!hIcon) hIcon = (HICON) GetClassLongA(wndPtr->hwndSelf, GCL_HICON);
/* If there is no hIcon specified or this is not a modal dialog, */
/* get the default one. */
if(hIcon == 0)
if (!(wndPtr->dwStyle & DS_MODALFRAME))
hIcon = LoadImageA(0, MAKEINTRESOURCEA(OIC_WINEICON), IMAGE_ICON, 0, 0, LR_DEFAULTCOLOR);
hIcon = NC_IconForWindow( wndPtr );
if (hIcon)
DrawIconEx (hdc, rect.left + 2, rect.top + 2, hIcon,
......@@ -2856,3 +2842,16 @@ BOOL NC_DrawGrayButton(HDC hdc, int x, int y)
return TRUE;
}
HICON16 NC_IconForWindow(WND *wndPtr)
{
HICON16 hIcon = (HICON) GetClassLongA(wndPtr->hwndSelf, GCL_HICONSM);
if(!hIcon) hIcon = (HICON) GetClassLongA(wndPtr->hwndSelf, GCL_HICON);
/* If there is no hIcon specified and this is a modal dialog, */
/* get the default one. */
if (!hIcon && (wndPtr->dwStyle & DS_MODALFRAME))
hIcon = LoadImageA(0, MAKEINTRESOURCEA(OIC_WINEICON), IMAGE_ICON, 0, 0, LR_DEFAULTCOLOR);
return hIcon;
}
......@@ -156,6 +156,107 @@ BOOL X11DRV_WND_CreateDesktopWindow(WND *wndPtr, CLASS *classPtr, BOOL bUnicode)
return TRUE;
}
/**********************************************************************
* X11DRV_WND_IconChanged
*
* hIcon or hIconSm has changed (or is being initialised for the
* first time). Complete the X11 driver-specific initialisation.
*
* This is not entirely correct, may need to create
* an icon window and set the pixmap as a background
*/
static void X11DRV_WND_IconChanged(WND *wndPtr)
{
HICON16 hIcon = NC_IconForWindow(wndPtr);
if( ((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap )
DeleteObject( ((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap );
if( ((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask )
DeleteObject( ((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask);
if (!hIcon)
{
((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap= 0;
((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask= 0;
}
else
{
HBITMAP hbmOrig;
RECT rcMask;
BITMAP bmMask;
ICONINFO ii;
HDC hDC;
GetIconInfo(hIcon, &ii);
X11DRV_CreateBitmap(ii.hbmMask);
X11DRV_CreateBitmap(ii.hbmColor);
GetObjectA(ii.hbmMask, sizeof(bmMask), &bmMask);
rcMask.top = 0;
rcMask.left = 0;
rcMask.right = bmMask.bmWidth;
rcMask.bottom = bmMask.bmHeight;
hDC = CreateCompatibleDC(0);
hbmOrig = SelectObject(hDC, ii.hbmMask);
InvertRect(hDC, &rcMask);
SelectObject(hDC, hbmOrig);
DeleteDC(hDC);
((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap = ii.hbmColor;
((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask= ii.hbmMask;
}
return;
}
static void X11DRV_WND_SetIconHints(WND *wndPtr, XWMHints *hints)
{
if (((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap)
{
hints->icon_pixmap
= X11DRV_BITMAP_Pixmap(((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap);
hints->flags |= IconPixmapHint;
}
else
hints->flags &= ~IconPixmapHint;
if (((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask)
{
hints->icon_mask
= X11DRV_BITMAP_Pixmap(((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask);
hints->flags |= IconMaskHint;
}
else
hints->flags &= ~IconMaskHint;
}
/**********************************************************************
* X11DRV_WND_UpdateIconHints
*
* hIcon or hIconSm has changed (or is being initialised for the
* first time). Complete the X11 driver-specific initialisation
* and set the window hints.
*
* This is not entirely correct, may need to create
* an icon window and set the pixmap as a background
*/
static void X11DRV_WND_UpdateIconHints(WND *wndPtr)
{
XWMHints* wm_hints;
X11DRV_WND_IconChanged(wndPtr);
wm_hints = TSXAllocWMHints();
X11DRV_WND_SetIconHints(wndPtr, wm_hints);
TSXSetWMHints( display, X11DRV_WND_GetXWindow(wndPtr), wm_hints );
TSXFree( wm_hints );
}
/**********************************************************************
* X11DRV_WND_CreateWindow
......@@ -196,6 +297,7 @@ BOOL X11DRV_WND_CreateWindow(WND *wndPtr, CLASS *classPtr, CREATESTRUCTA *cs, BO
win_attr.cursor = X11DRV_MOUSE_XCursor;
((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap = 0;
((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask = 0;
((X11DRV_WND_DATA *) wndPtr->pDriverData)->bit_gravity = win_attr.bit_gravity;
((X11DRV_WND_DATA *) wndPtr->pDriverData)->window =
TSXCreateWindow( display, X11DRV_GetXRootWindow(),
......@@ -267,28 +369,9 @@ BOOL X11DRV_WND_CreateWindow(WND *wndPtr, CLASS *classPtr, CREATESTRUCTA *cs, BO
if( wndPtr->flags & WIN_MANAGED )
{
if( wndPtr->class->hIcon )
{
CURSORICONINFO *ptr;
if( (ptr = (CURSORICONINFO *)GlobalLock16( wndPtr->class->hIcon )) )
{
/* This is not entirely correct, may need to create
* an icon window and set the pixmap as a background */
HBITMAP hBitmap = CreateBitmap( ptr->nWidth, ptr->nHeight,
ptr->bPlanes, ptr->bBitsPerPixel, (char *)(ptr + 1) +
ptr->nHeight * BITMAP_GetWidthBytes(ptr->nWidth,1) );
if( hBitmap )
{
((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap = hBitmap;
X11DRV_CreateBitmap( hBitmap );
wm_hints->flags |= IconPixmapHint;
wm_hints->icon_pixmap = X11DRV_BITMAP_Pixmap( hBitmap );
}
}
}
X11DRV_WND_IconChanged(wndPtr);
X11DRV_WND_SetIconHints(wndPtr, wm_hints);
wm_hints->initial_state = (wndPtr->dwStyle & WS_MINIMIZE)
? IconicState : NormalState;
}
......@@ -323,6 +406,11 @@ BOOL X11DRV_WND_DestroyWindow(WND *wndPtr)
DeleteObject( ((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap );
((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconBitmap = 0;
}
if( ((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask )
{
DeleteObject( ((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask);
((X11DRV_WND_DATA *) wndPtr->pDriverData)->hWMIconMask= 0;
}
}
return TRUE;
......@@ -848,6 +936,11 @@ BOOL X11DRV_WND_SetHostAttr(WND* wnd, INT ha, INT value)
}
return TRUE;
case HAK_ICONS: /* called when the icons change */
if ( (wnd->flags & WIN_MANAGED) )
X11DRV_WND_UpdateIconHints(wnd);
return TRUE;
case HAK_ACCEPTFOCUS: /* called when a window is disabled/enabled */
if( (wnd->flags & WIN_MANAGED) )
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment