void fnTrayIconUpdateWithImageList(int iImage, const TCHAR *szNewTip, char *szPreferredProto) { HICON hIcon = ImageList_GetIcon(hCListImages, iImage, ILD_NORMAL); cli.pfnTrayIconUpdate(hIcon, szNewTip, szPreferredProto, 0); DestroyIcon(hIcon); }
/***************************************************************************** * SIC_OverlayShortcutImage [internal] * * NOTES * Creates a new icon as a copy of the passed-in icon, overlayed with a * shortcut image. * FIXME: This should go to the ImageList implementation! */ static HICON SIC_OverlayShortcutImage(HICON SourceIcon, BOOL large) { ICONINFO ShortcutIconInfo, TargetIconInfo; HICON ShortcutIcon = NULL, TargetIcon; BITMAP TargetBitmapInfo, ShortcutBitmapInfo; HDC ShortcutDC = NULL, TargetDC = NULL; HBITMAP OldShortcutBitmap = NULL, OldTargetBitmap = NULL; static int s_imgListIdx = -1; ZeroMemory(&ShortcutIconInfo, sizeof(ShortcutIconInfo)); ZeroMemory(&TargetIconInfo, sizeof(TargetIconInfo)); /* Get information about the source icon and shortcut overlay. * We will write over the source bitmaps to get the final ones */ if (! GetIconInfo(SourceIcon, &TargetIconInfo)) return NULL; /* Is it possible with the ImageList implementation? */ if(!TargetIconInfo.hbmColor) { /* Maybe we'll support this at some point */ FIXME("1bpp icon wants its overlay!\n"); goto fail; } if(!GetObjectW(TargetIconInfo.hbmColor, sizeof(BITMAP), &TargetBitmapInfo)) { goto fail; } /* search for the shortcut icon only once */ if (s_imgListIdx == -1) s_imgListIdx = SIC_LoadOverlayIcon(- IDI_SHELL_SHORTCUT); /* FIXME should use icon index 29 instead of the resource id, but not all icons are present yet so we can't use icon indices */ if (s_imgListIdx != -1) { if (large) ShortcutIcon = ImageList_GetIcon(ShellBigIconList, s_imgListIdx, ILD_TRANSPARENT); else ShortcutIcon = ImageList_GetIcon(ShellSmallIconList, s_imgListIdx, ILD_TRANSPARENT); } else ShortcutIcon = NULL; if (!ShortcutIcon || !GetIconInfo(ShortcutIcon, &ShortcutIconInfo)) { goto fail; } /* Is it possible with the ImageLists ? */ if(!ShortcutIconInfo.hbmColor) { /* Maybe we'll support this at some point */ FIXME("Should draw 1bpp overlay!\n"); goto fail; } if(!GetObjectW(ShortcutIconInfo.hbmColor, sizeof(BITMAP), &ShortcutBitmapInfo)) { goto fail; } /* Setup the masks */ ShortcutDC = CreateCompatibleDC(NULL); if (NULL == ShortcutDC) goto fail; OldShortcutBitmap = (HBITMAP)SelectObject(ShortcutDC, ShortcutIconInfo.hbmMask); if (NULL == OldShortcutBitmap) goto fail; TargetDC = CreateCompatibleDC(NULL); if (NULL == TargetDC) goto fail; OldTargetBitmap = (HBITMAP)SelectObject(TargetDC, TargetIconInfo.hbmMask); if (NULL == OldTargetBitmap) goto fail; /* Create the complete mask by ANDing the source and shortcut masks. * NOTE: in an ImageList, all icons have the same dimensions */ if (!BitBlt(TargetDC, 0, 0, ShortcutBitmapInfo.bmWidth, ShortcutBitmapInfo.bmHeight, ShortcutDC, 0, 0, SRCAND)) { goto fail; } /* * We must remove or add the alpha component to the shortcut overlay: * If we don't, SRCCOPY will copy it to our resulting icon, resulting in a * partially transparent icons where it shouldn't be, and to an invisible icon * if the underlying icon don't have any alpha channel information. (16bpp only icon for instance). * But if the underlying icon has alpha channel information, then we must mark the overlay information * as opaque. * NOTE: This code sucks(tm) and should belong to the ImageList implementation. * NOTE2: there are better ways to do this. */ if(ShortcutBitmapInfo.bmBitsPixel == 32) { BOOL add_alpha; BYTE buffer[sizeof(BITMAPINFO) + 256 * sizeof(RGBQUAD)]; BITMAPINFO* lpbmi = (BITMAPINFO*)buffer; PVOID bits; PULONG pixel; INT i, j; /* Find if the source bitmap has an alpha channel */ if(TargetBitmapInfo.bmBitsPixel != 32) add_alpha = FALSE; else { ZeroMemory(buffer, sizeof(buffer)); lpbmi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER); lpbmi->bmiHeader.biWidth = TargetBitmapInfo.bmWidth; lpbmi->bmiHeader.biHeight = TargetBitmapInfo.bmHeight; lpbmi->bmiHeader.biPlanes = 1; lpbmi->bmiHeader.biBitCount = 32; bits = HeapAlloc(GetProcessHeap(), 0, TargetBitmapInfo.bmHeight * TargetBitmapInfo.bmWidthBytes); if(!bits) goto fail; if(!GetDIBits(TargetDC, TargetIconInfo.hbmColor, 0, TargetBitmapInfo.bmHeight, bits, lpbmi, DIB_RGB_COLORS)) { ERR("GetBIBits failed!\n"); HeapFree(GetProcessHeap(), 0, bits); goto fail; } i = j = 0; pixel = (PULONG)bits; for(i=0; i<TargetBitmapInfo.bmHeight; i++) { for(j=0; j<TargetBitmapInfo.bmWidth; j++) { add_alpha = (*pixel++ & 0xFF000000) != 0; if(add_alpha) break; } if(add_alpha) break; } HeapFree(GetProcessHeap(), 0, bits); } /* Allocate the bits */ bits = HeapAlloc(GetProcessHeap(), 0, ShortcutBitmapInfo.bmHeight*ShortcutBitmapInfo.bmWidthBytes); if(!bits) goto fail; ZeroMemory(buffer, sizeof(buffer)); lpbmi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER); lpbmi->bmiHeader.biWidth = ShortcutBitmapInfo.bmWidth; lpbmi->bmiHeader.biHeight = ShortcutBitmapInfo.bmHeight; lpbmi->bmiHeader.biPlanes = 1; lpbmi->bmiHeader.biBitCount = 32; if(!GetDIBits(TargetDC, ShortcutIconInfo.hbmColor, 0, ShortcutBitmapInfo.bmHeight, bits, lpbmi, DIB_RGB_COLORS)) { ERR("GetBIBits failed!\n"); HeapFree(GetProcessHeap(), 0, bits); goto fail; } pixel = (PULONG)bits; /* Remove alpha channel component or make it totally opaque */ for(i=0; i<ShortcutBitmapInfo.bmHeight; i++) { for(j=0; j<ShortcutBitmapInfo.bmWidth; j++) { if(add_alpha) *pixel++ |= 0xFF000000; else *pixel++ &= 0x00FFFFFF; } } /* GetDIBits return BI_BITFIELDS with masks set to 0, and SetDIBits fails when masks are 0. The irony... */ lpbmi->bmiHeader.biCompression = BI_RGB; /* Set the bits again */ if(!SetDIBits(TargetDC, ShortcutIconInfo.hbmColor, 0, ShortcutBitmapInfo.bmHeight, bits, lpbmi, DIB_RGB_COLORS)) { ERR("SetBIBits failed!, %lu\n", GetLastError()); HeapFree(GetProcessHeap(), 0, bits); goto fail; } HeapFree(GetProcessHeap(), 0, bits); } /* Now do the copy. We overwrite the original icon data */ if (NULL == SelectObject(ShortcutDC, ShortcutIconInfo.hbmColor) || NULL == SelectObject(TargetDC, TargetIconInfo.hbmColor)) goto fail; if (!MaskBlt(TargetDC, 0, 0, ShortcutBitmapInfo.bmWidth, ShortcutBitmapInfo.bmHeight, ShortcutDC, 0, 0, ShortcutIconInfo.hbmMask, 0, 0, MAKEROP4(0xAA0000, SRCCOPY))) { goto fail; } /* Clean up, we're not goto'ing to 'fail' after this so we can be lazy and not set handles to NULL */ SelectObject(TargetDC, OldTargetBitmap); DeleteDC(TargetDC); SelectObject(ShortcutDC, OldShortcutBitmap); DeleteDC(ShortcutDC); /* Create the icon using the bitmaps prepared earlier */ TargetIcon = CreateIconIndirect(&TargetIconInfo); /* CreateIconIndirect copies the bitmaps, so we can release our bitmaps now */ DeleteObject(TargetIconInfo.hbmColor); DeleteObject(TargetIconInfo.hbmMask); /* Delete what GetIconInfo gave us */ DeleteObject(ShortcutIconInfo.hbmColor); DeleteObject(ShortcutIconInfo.hbmMask); DestroyIcon(ShortcutIcon); return TargetIcon; fail: /* Clean up scratch resources we created */ if (NULL != OldTargetBitmap) SelectObject(TargetDC, OldTargetBitmap); if (NULL != TargetDC) DeleteDC(TargetDC); if (NULL != OldShortcutBitmap) SelectObject(ShortcutDC, OldShortcutBitmap); if (NULL != ShortcutDC) DeleteDC(ShortcutDC); if (NULL != TargetIconInfo.hbmColor) DeleteObject(TargetIconInfo.hbmColor); if (NULL != TargetIconInfo.hbmMask) DeleteObject(TargetIconInfo.hbmMask); if (NULL != ShortcutIconInfo.hbmColor) DeleteObject(ShortcutIconInfo.hbmColor); if (NULL != ShortcutIconInfo.hbmMask) DeleteObject(ShortcutIconInfo.hbmMask); if (NULL != ShortcutIcon) DestroyIcon(ShortcutIcon); return NULL; }
static void button_paint_split(HWND win, button_t* button, HDC dc) { RECT rect; RECT rect_left, rect_right; int state_left, state_right; int text_offset = 0; HFONT font, old_font; int old_bk_mode; COLORREF old_text_color; HRGN old_clip; HICON glyph; int width_right = DROPDOWN_W; glyph = ImageList_GetIcon(mc_bmp_glyphs, MC_BMP_GLYPH_MORE_OPTIONS, ILD_TRANSPARENT); GetClientRect(win, &rect); font = (HFONT) MC_SEND(win, WM_GETFONT, 0, 0); if(font == NULL) font = GetStockObject(SYSTEM_FONT); old_font = SelectObject(dc, font); old_bk_mode = GetBkMode(dc); old_text_color = GetTextColor(dc); old_clip = get_clip(dc); /* Draw what's common for left and right parts background. */ if(!button->theme && (button->style & BS_DEFPUSHBUTTON)) { SelectObject(dc, GetSysColorBrush(COLOR_WINDOWFRAME)); Rectangle(dc, rect.left, rect.top, rect.right, rect.bottom); mc_rect_inflate(&rect, -1, -1); width_right--; } /* Setup subrectangles (mainpart 1 and push-down part 2) */ mc_rect_copy(&rect_left, &rect); rect_left.right -= width_right; mc_rect_copy(&rect_right, &rect); rect_right.left = rect_left.right; /* Draw background. */ if(button->theme) { UINT transparent; RECT tmp; /* Determine styles for left and right parts */ if(button->style & WS_DISABLED) { state_left = state_right = PBS_DISABLED; } else { LRESULT state; state = MC_SEND(win, BM_GETSTATE, 0, 0); if(state & MC_BST_DROPDOWNPUSHED) { state_left = PBS_NORMAL; state_right = PBS_PRESSED; } else { if(state & BST_PUSHED) state_left = state_right = PBS_PRESSED; else if(state & BST_HOT) state_left = state_right = PBS_HOT; else if(button->style & BS_DEFPUSHBUTTON) state_left = state_right = PBS_DEFAULTED; else state_left = state_right = PBS_NORMAL; } } /* Handle (semi-)transparent themes. */ transparent = 0; if(mcIsThemeBackgroundPartiallyTransparent(button->theme, BP_PUSHBUTTON, state_left)) transparent |= 0x1; if(mcIsThemeBackgroundPartiallyTransparent(button->theme, BP_PUSHBUTTON, state_right)) transparent |= 0x2; switch(transparent) { case 0x1: mcDrawThemeParentBackground(win, dc, &rect_left); break; case 0x2: mcDrawThemeParentBackground(win, dc, &rect_right); break; case 0x3: mcDrawThemeParentBackground(win, dc, &rect); break; } /* Draw backgrond. */ mcDrawThemeBackground(button->theme, dc, BP_PUSHBUTTON, state_left, &rect, &rect_left); mcDrawThemeBackground(button->theme, dc, BP_PUSHBUTTON, state_right, &rect, &rect_right); /* Deflate both rects to content rects only */ mcGetThemeBackgroundContentRect(button->theme, dc, BP_PUSHBUTTON, state_left, &rect_left, &tmp); rect_left.left = tmp.left; rect_left.top = tmp.top; rect_left.bottom = tmp.bottom; mcGetThemeBackgroundContentRect(button->theme, dc, BP_PUSHBUTTON, state_right, &rect_right, &tmp); rect_right.top = tmp.top; rect_right.right = tmp.right; rect_right.bottom = tmp.bottom; /* Draw delimiter of left and right parts. */ rect_right.top += 1; rect_right.bottom -= 1; mcDrawThemeEdge(button->theme, dc, BP_PUSHBUTTON, state_right, &rect_right, BDR_SUNKEN, BF_LEFT, NULL); rect_right.left = tmp.left; } else { /* Determine styles for left and right parts */ if(button->style & WS_DISABLED) { state_left = state_right = DFCS_INACTIVE; } else { LRESULT s = MC_SEND(win, BM_GETSTATE, 0, 0); if(s & MC_BST_DROPDOWNPUSHED) { state_left = 0; state_right = DFCS_PUSHED; } else { if(s & BST_PUSHED) { state_left = state_right = DFCS_PUSHED; } else { state_left = state_right = 0; } } } button_send_ctlcolorbtn(win, dc); /* Draw control edges */ IntersectClipRect(dc, rect_left.left, rect_left.top, rect_left.right, rect_left.bottom); DrawFrameControl(dc, &rect, DFC_BUTTON, DFCS_BUTTONPUSH | state_left); SelectClipRgn(dc, NULL); IntersectClipRect(dc, rect_right.left, rect_right.top, rect_right.right, rect_right.bottom); DrawFrameControl(dc, &rect, DFC_BUTTON, DFCS_BUTTONPUSH | state_right); /* Parts which are pushed, should have the contents moved a bit */ if(state_left == DFCS_PUSHED) mc_rect_offset(&rect_left, 1, 1); if(state_right == DFCS_PUSHED) mc_rect_offset(&rect_right, 1, 1); /* Draw delimiter */ if(state_left == state_right) { DrawEdge(dc, &rect_right, BDR_SUNKENOUTER | BDR_RAISEDINNER, BF_LEFT | BF_SOFT); } else { rect_right.left--; DrawEdge(dc, &rect_right, BDR_SUNKENOUTER, BF_LEFT | BF_SOFT); rect_right.left++; } /* Adjust for the outer control edges */ mc_rect_inflate(&rect_left, 0, -2); rect_left.left += 2; mc_rect_inflate(&rect_right, -2, -2); } /* Draw focus rectangle. */ if((MC_SEND(win, BM_GETSTATE, 0, 0) & BST_FOCUS) && !button->hide_focus) { SelectClipRgn(dc, NULL); if(button->theme) { mc_rect_set(&rect, rect_left.left, rect_left.top, rect_right.right - DROPDOWN_W, rect_right.bottom); DrawFocusRect(dc, &rect); } else { mc_rect_inflate(&rect_left, -1, -2); DrawFocusRect(dc, &rect_left); mc_rect_inflate(&rect_left, -1, -1); } } /* Draw glyph into the right part */ SelectClipRgn(dc, NULL); IntersectClipRect(dc, rect_right.left, rect_right.top, rect_right.right, rect_right.bottom); DrawIconEx(dc, (rect_right.right + rect_right.left - MC_BMP_GLYPH_W) / 2, (rect_right.bottom + rect_right.top - MC_BMP_GLYPH_H) / 2, glyph, MC_BMP_GLYPH_W, MC_BMP_GLYPH_H, 0, NULL, DI_NORMAL); /* Draw left part contents */ SelectClipRgn(dc, NULL); IntersectClipRect(dc, rect_left.left, rect_left.top, rect_left.right, rect_left.bottom); if(button->style & BS_ICON) { /* Paint (BS_SPLITBUTTON | BS_ICON). Note that this is used even on * Vista, as according to some my testing this style combination * is not supported there... */ HICON icon; icon = (HICON) MC_SEND(win, BM_GETIMAGE, (WPARAM) IMAGE_ICON, (LPARAM) 0); if(icon != NULL) { SIZE size; UINT flags; mc_icon_size(icon, &size); flags = DST_ICON; if(button->style & WS_DISABLED) flags |= DSS_DISABLED; DrawState(dc, NULL, NULL, (LPARAM) icon, 0, (rect_left.right + rect_left.left - size.cx) / 2, (rect_left.bottom + rect_left.top - size.cy) / 2, size.cx, size.cy, flags); } } else { /* Paint text label */ TCHAR buffer[256]; int n; UINT flags = 0; /* Setup flags for TextOut/mcDrawThemeText */ switch(button->style & (BS_LEFT | BS_CENTER | BS_RIGHT)) { case BS_LEFT: flags |= DT_LEFT; break; case BS_RIGHT: flags |= DT_RIGHT; break; default: if(GetWindowLong(win, GWL_EXSTYLE) & WS_EX_RIGHT) flags |= DT_RIGHT; else flags |= DT_CENTER; break; } switch(button->style & (BS_TOP | BS_VCENTER | BS_BOTTOM)) { case BS_TOP: flags |= DT_TOP; break; case BS_BOTTOM: flags |= DT_BOTTOM; break; default: flags |= DT_VCENTER; break; } if(button->style & BS_MULTILINE) flags |= DT_WORDBREAK; else flags |= DT_SINGLELINE; if(button->hide_accel) flags |= DT_HIDEPREFIX; n = MC_SEND(win, WM_GETTEXT, MC_SIZEOF_ARRAY(buffer), buffer); if(button->theme) { mcDrawThemeText(button->theme, dc, BP_PUSHBUTTON, state_left, buffer, n, flags, 0, &rect_left); } else { SetBkMode(dc, TRANSPARENT); SetTextColor(dc, GetSysColor(COLOR_BTNTEXT)); mc_rect_offset(&rect_left, text_offset, text_offset); DrawText(dc, buffer, n, &rect_left, flags); } } SelectObject(dc, old_font); SetBkMode(dc, old_bk_mode); SetTextColor(dc, old_text_color); SelectObject(dc, old_clip); }
// WM_COMMAND handler. LRESULT KeyboardPage::OnCommand( UINT nNotifyCode, UINT nCtrlID, HWND hWndCtrl ) { // What's up? switch ( nCtrlID ) { case EditToolbar::ETID_NEW: // Command toolbar? if ( hWndCtrl == m_ComTools ) { // Obtain button rectangle. ClsRect rc; m_ComTools.GetItemRect( 0, rc ); // Convert rectangle to screen // coordinates. m_ComTools.ClientToScreen( rc ); // Show the menu. ::TrackPopupMenuEx( m_Menu,//*m_Menu.GetSubMenu( 0 ), TPM_LEFTALIGN, rc.Left(), rc.Bottom(), GetSafeHWND(), NULL ); } else { // Show the key recorder. KeyRec kr; ClsString str; if ( kr.KeyRecord( *GetParent(), str )) AddKeyMapping( str ); } return 0; case EditToolbar::ETID_DELETE: // Command toolbar? if ( hWndCtrl == m_ComTools ) { // Get current selection. LPCNODE pCNode = ( LPCNODE )m_Commands.GetItemData( m_Commands.GetCurSel()); if ( pCNode != ( LPCNODE )LB_ERR ) { // Save selection position. int nSel = m_Commands.GetCurSel(); int nPos = nSel; int nMax = m_Commands.GetCount(); // Select the next or previous // entry. if ( nSel == nMax - 1 && nSel ) nSel--; else nSel++; // Select the new item m_Commands.SetCurSel( nSel ); // Remove the node from the listview. m_Commands.DeleteString( nPos ); // Remove it from the command list. Remove(( LPNODE )pCNode ); // Free the node // data. if ( pCNode->nType != CTYPE_HARDCODED ) ::FreePooled( pParserPool, pCNode->pcStr ); // And the node itself. ::FreePooled( pParserPool, pCNode ); // Setup GUI. SetupControls(); pSettings->Changed( m_pParser ); } return 0; } else { // Get the key descriptor. TCHAR szKeyString[ 64 ]; int nSel = m_Keys.GetCurSel(), nMax = m_Keys.GetCount(); if ( nSel != LB_ERR ) { if ( m_Keys.GetText( nSel, szKeyString ) != LB_ERR ) { // Convert to a code and qualifier. TCHAR cCode, cQual; if ( ::Str2CodeQual( szKeyString, &cCode, &cQual )) { // Remove the hash. This will automatically destroy // the command-list aswell. ::RemHash( pParserPool, m_pParser->aHash, cCode, cQual ); // Remove it from the listview. m_Keys.DeleteString( nSel ); // Was it the last one? if ( nSel == nMax - 1 ) nSel--; // Select the next or previous key. m_Keys.SetCurSel( nSel ); SendMessage( WM_COMMAND, MAKEWPARAM( IDC_KEYS, LBN_SELCHANGE ), ( LPARAM )m_Keys.GetSafeHWND()); // Changes made... pSettings->Changed( m_pParser ); } } } } return 0; case EditToolbar::ETID_UP: { // Valid node? LPCNODE pCNode = ( LPCNODE )m_Commands.GetItemData( m_Commands.GetCurSel()); if ( pCNode != ( LPCNODE )LB_ERR ) { // Get it's predecessor. LPCNODE pCPrev = pCNode->lpPrev; // Swap both data entries. CNODE cTemp; cTemp.nType = pCPrev->nType; cTemp.uCommand = pCPrev->uCommand; pCPrev->nType = pCNode->nType; pCPrev->uCommand = pCNode->uCommand; pCNode->nType = cTemp.nType; pCNode->uCommand = cTemp.uCommand; // Select the previous item which // in fact is the already selected // item. m_Commands.SetCurSel( m_Commands.GetCurSel() - 1 ); SetupControls(); pSettings->Changed( m_pParser ); return 0; } } case EditToolbar::ETID_DOWN: { // Valid node? LPCNODE pCNode = ( LPCNODE )m_Commands.GetItemData( m_Commands.GetCurSel()); if ( pCNode != ( LPCNODE )LB_ERR ) { // Get it's successor. LPCNODE pCNext = pCNode->lpNext; // Swap both data entries. CNODE cTemp; cTemp.nType = pCNext->nType; cTemp.uCommand = pCNext->uCommand; pCNext->nType = pCNode->nType; pCNext->uCommand = pCNode->uCommand; pCNode->nType = cTemp.nType; pCNode->uCommand = cTemp.uCommand; // Select the next item which // in fact is the already selected // item. m_Commands.SetCurSel( m_Commands.GetCurSel() + 1 ); SetupControls(); pSettings->Changed( m_pParser ); return 0; } } case IDS_INSERT: CreateNode( CTYPE_TEXT, ( LPVOID )( LPCTSTR )ClsString( MAKEINTRESOURCE( IDS_NEWINSERT ))); return 0; case IDS_HARDCODED: CreateNode( CTYPE_HARDCODED, ( LPVOID )( ::GetCommandTable()->nCommandID )); return 0; case IDS_RUN: CreateNode( CTYPE_RUN, ( LPVOID )( _T( "Calc.exe" ))); return 0; case IDS_OPEN: CreateNode( CTYPE_SHELLOPEN, ( LPVOID )( _T( "ReadMe.txt" ))); return 0; case IDC_KEYS: if ( nNotifyCode == LBN_SELCHANGE ) { // Get the current selection. LPHASH pSel = GetSelection(); if ( pSel ) { // Clear the contents of the command list. m_Commands.ResetContent(); // Add commands. LPCNODE pNode; for ( pNode = pSel->lpCommands->lpFirst; pNode->lpNext; pNode = pNode->lpNext ) m_Commands.AddString(( LPCTSTR )pNode ); } } // Setup controls. SetupControls(); return 0; case IDC_COMMANDS: // Double-click? if ( nNotifyCode == LBN_DBLCLK ) { // Find the command node. LPCNODE pCNode = ( LPCNODE )m_Commands.GetItemData( m_Commands.GetCurSel()); if ( pCNode != ( LPCNODE )LB_ERR ) { // What's the type? switch ( pCNode->nType ) { case CTYPE_HARDCODED: { // Open the editor. Hardcoded h; if ( h.Select( *GetParent(), pCNode )) { // Refresh list. m_Commands.Invalidate(); pSettings->Changed( m_pParser ); } break; } case CTYPE_TEXT: { // Open the editor. TextInsert ti; HICON hIcon = ImageList_GetIcon( m_hImages, 1, ILD_NORMAL ); if ( ti.Edit( *GetParent(), pCNode, hIcon )) { // Refresh list. m_Commands.Invalidate(); pSettings->Changed( m_pParser ); } if ( hIcon ) ::DestroyIcon( hIcon ); return 0; } case CTYPE_RUN: case CTYPE_SHELLOPEN: { // Open the editor. Run r; if ( r.Edit( *GetParent(), pCNode )) { // Refresh list. m_Commands.Invalidate(); pSettings->Changed( m_pParser ); } } } } } else // Setup GUI. SetupControls(); return 0; } // Pass to the base class. return Page::OnCommand( nNotifyCode, nCtrlID, hWndCtrl ); }
int CIconList::CreateTabIconInt(LPCWSTR asIconDescr, bool bAdmin, LPCWSTR asWorkDir) { wchar_t* pszExpanded = ExpandEnvStr(asIconDescr); // Need to be created! int iIconIdx = -1; HICON hFileIcon = NULL; CEStr szLoadFile; LPCWSTR lpszExt = NULL; int nIndex = 0; bool bDirChanged = false; if (!szLoadFile.Set(pszExpanded ? pszExpanded : asIconDescr)) { goto wrap; } lpszExt = ParseIconFileIndex(szLoadFile, nIndex); if (asWorkDir && *asWorkDir) { // Executable (or icon) file may be not availbale by %PATH%, let "cd" to it... bDirChanged = gpConEmu->ChangeWorkDir(asWorkDir); } if (!lpszExt) { if (apiSearchPath(NULL, szLoadFile, L".exe", szLoadFile)) { lpszExt = PointToExt(szLoadFile); } if (!lpszExt) goto wrap; } if (lstrcmpi(lpszExt, L".ico") == 0) { hFileIcon = (HICON)LoadImage(0, szLoadFile, IMAGE_ICON, mn_CxIcon, mn_CyIcon, LR_DEFAULTCOLOR|LR_LOADFROMFILE); } else if ((lstrcmpi(lpszExt, L".exe") == 0) || (lstrcmpi(lpszExt, L".dll") == 0)) { HICON hIconLarge = NULL, hIconSmall = NULL; ExtractIconEx(szLoadFile, nIndex, &hIconLarge, &hIconSmall, 1); bool bUseLargeIcon = ((mn_CxIcon > 16) && (hIconLarge != NULL)) || (hIconSmall == NULL); HICON hDestroyIcon = bUseLargeIcon ? hIconSmall : hIconLarge; if (hDestroyIcon) DestroyIcon(hDestroyIcon); hFileIcon = bUseLargeIcon ? hIconLarge : hIconSmall; } else { //TODO: Shell icons for registered files (cmd, bat, sh, pl, py, ...) } if (hFileIcon) { wchar_t szIconInfo[80] = L"", szMergedInfo[80] = L""; GetIconInfoStr(hFileIcon, szIconInfo); if (gpSetCls->isAdvLogging) { CEStr lsLog(lstrmerge(L"Icon `", asIconDescr, L"` was loaded: ", szIconInfo)); gpConEmu->LogString(lsLog); } int iIconIdxAdm = -1; iIconIdx = ImageList_ReplaceIcon(mh_TabIcons, -1, hFileIcon); TabIconCache NewIcon = {lstrdup(asIconDescr), iIconIdx, false}; m_Icons.push_back(NewIcon); if (mn_AdminIcon >= 0) { HIMAGELIST hAdmList = ImageList_Merge(mh_TabIcons, iIconIdx, mh_TabIcons, mn_AdminIcon+2, 0,0); if (hAdmList) { HICON hNewIcon = ImageList_GetIcon(hAdmList, 0, ILD_TRANSPARENT); if (hNewIcon) { CEStr lsLog(lstrmerge(L"Admin icon `", asIconDescr, L"` was created: ", GetIconInfoStr(hNewIcon, szMergedInfo))); gpConEmu->LogString(lsLog); iIconIdxAdm = ImageList_ReplaceIcon(mh_TabIcons, -1, hNewIcon); DestroyIcon(hNewIcon); TabIconCache AdmIcon = {lstrdup(asIconDescr), iIconIdxAdm, true}; m_Icons.push_back(AdmIcon); if (bAdmin && (iIconIdxAdm > 0)) { iIconIdx = iIconIdxAdm; } } else { gpConEmu->LogString(L"GetIcon for admin icon was failed"); } ImageList_Destroy(hAdmList); } else { gpConEmu->LogString(L"Admin icon merging was failed"); } } DestroyIcon(hFileIcon); } wrap: if (bDirChanged) { gpConEmu->ChangeWorkDir(NULL); } SafeFree(pszExpanded); if (gpSetCls->isAdvLogging && (iIconIdx < 0)) { CEStr lsLog(lstrmerge(L"Icon `", asIconDescr, L"` loading was failed")); gpConEmu->LogString(lsLog); } return iIconIdx; }
QIcon QFileIconProviderPrivate::getWinIcon(const QFileInfo &fileInfo) const { QIcon retIcon; static int defaultFolderIIcon = -1; QString key; QPixmap pixmap; // If it's a file, non-{exe,lnk,ico} then we might have it cached already if (isCacheable(fileInfo)) { const QString fileExtension = QLatin1Char('.') + fileInfo.suffix().toUpper(); key = QLatin1String("qt_") + fileExtension; QPixmapCache::find(key, pixmap); if (!pixmap.isNull()) { retIcon.addPixmap(pixmap); if (QPixmapCache::find(key + QLatin1Char('l'), pixmap)) retIcon.addPixmap(pixmap); return retIcon; } } const bool cacheableDirIcon = fileInfo.isDir() && !fileInfo.isRoot(); if (!useCustomDirectoryIcons && defaultFolderIIcon >= 0 && cacheableDirIcon) { // We already have the default folder icon, just return it key = QString::fromLatin1("qt_dir_%1").arg(defaultFolderIIcon); QPixmapCache::find(key, pixmap); if (!pixmap.isNull()) { retIcon.addPixmap(pixmap); if (QPixmapCache::find(key + QLatin1Char('l'), pixmap)) retIcon.addPixmap(pixmap); return retIcon; } } /* We don't use the variable, but by storing it statically, we * ensure CoInitialize is only called once. */ static HRESULT comInit = CoInitialize(NULL); Q_UNUSED(comInit); SHFILEINFO info; unsigned long val = 0; //Get the small icon unsigned int flags = #ifndef Q_OS_WINCE SHGFI_ICON|SHGFI_SYSICONINDEX|SHGFI_ADDOVERLAYS|SHGFI_OVERLAYINDEX; #else SHGFI_SYSICONINDEX; #endif if (cacheableDirIcon && !useCustomDirectoryIcons) { flags |= SHGFI_USEFILEATTRIBUTES; val = SHGetFileInfo(L"dummy", FILE_ATTRIBUTE_DIRECTORY, &info, sizeof(SHFILEINFO), flags | SHGFI_SMALLICON); } else { val = SHGetFileInfo((const wchar_t *)QDir::toNativeSeparators(fileInfo.filePath()).utf16(), 0, &info, sizeof(SHFILEINFO), flags | SHGFI_SMALLICON); } // Even if GetFileInfo returns a valid result, hIcon can be empty in some cases if (val && info.hIcon) { if (fileInfo.isDir() && !fileInfo.isRoot()) { if (!useCustomDirectoryIcons && defaultFolderIIcon < 0) defaultFolderIIcon = info.iIcon; //using the unique icon index provided by windows save us from duplicate keys key = QString::fromLatin1("qt_dir_%1").arg(info.iIcon); QPixmapCache::find(key, pixmap); if (!pixmap.isNull()) { retIcon.addPixmap(pixmap); if (QPixmapCache::find(key + QLatin1Char('l'), pixmap)) retIcon.addPixmap(pixmap); DestroyIcon(info.hIcon); return retIcon; } } if (pixmap.isNull()) { #ifndef Q_OS_WINCE pixmap = QPixmap::fromWinHICON(info.hIcon); #else pixmap = QPixmap::fromWinHICON(ImageList_GetIcon((HIMAGELIST) val, info.iIcon, ILD_NORMAL)); #endif if (!pixmap.isNull()) { retIcon.addPixmap(pixmap); if (!key.isEmpty()) QPixmapCache::insert(key, pixmap); } else { qWarning("QFileIconProviderPrivate::getWinIcon() no small icon found"); } } DestroyIcon(info.hIcon); } //Get the big icon val = SHGetFileInfo((const wchar_t *)QDir::toNativeSeparators(fileInfo.filePath()).utf16(), 0, &info, sizeof(SHFILEINFO), flags | SHGFI_LARGEICON); if (val && info.hIcon) { if (fileInfo.isDir() && !fileInfo.isRoot()) { //using the unique icon index provided by windows save us from duplicate keys key = QString::fromLatin1("qt_dir_%1").arg(info.iIcon); } #ifndef Q_OS_WINCE pixmap = QPixmap::fromWinHICON(info.hIcon); #else pixmap = QPixmap::fromWinHICON(ImageList_GetIcon((HIMAGELIST) val, info.iIcon, ILD_NORMAL)); #endif if (!pixmap.isNull()) { retIcon.addPixmap(pixmap); if (!key.isEmpty()) QPixmapCache::insert(key + QLatin1Char('l'), pixmap); } else { qWarning("QFileIconProviderPrivate::getWinIcon() no large icon found"); } DestroyIcon(info.hIcon); } return retIcon; }
int CIconList::CreateTabIcon(LPCWSTR asIconDescr, bool bAdmin) { if (bAdmin && !gpSet->isAdminShield()) bAdmin = false; if (!asIconDescr || !*asIconDescr) return GetTabIcon(bAdmin); for (INT_PTR i = 0; i < m_Icons.size(); i++) { const TabIconCache& icn = m_Icons[i]; if ((icn.bAdmin!=FALSE) != bAdmin) continue; if (lstrcmpi(icn.pszIconDescr, asIconDescr) != 0) continue; // Already was created! return icn.nIconIdx; } wchar_t* pszExpanded = ExpandEnvStr(asIconDescr); // Need to be created! int iIconIdx = -1; HICON hFileIcon = NULL; wchar_t szTemp[MAX_PATH]; LPCWSTR pszLoadFile = pszExpanded ? pszExpanded : asIconDescr; LPCWSTR lpszExt = (wchar_t*)PointToExt(pszLoadFile); if (!lpszExt) { LPWSTR pszFile = NULL; if (SearchPath(NULL, pszLoadFile, L".exe", countof(szTemp), szTemp, &pszFile)) { pszLoadFile = szTemp; lpszExt = (wchar_t*)PointToExt(pszLoadFile); } if (!lpszExt) goto wrap; } if (lstrcmpi(lpszExt, L".ico") == 0) { hFileIcon = (HICON)LoadImage(0, pszLoadFile, IMAGE_ICON, GetSystemMetrics(SM_CXSMICON), GetSystemMetrics(SM_CYSMICON), LR_DEFAULTCOLOR|LR_LOADFROMFILE); } else if ((lstrcmpi(lpszExt, L".exe") == 0) || (lstrcmpi(lpszExt, L".dll") == 0)) { //TODO: May be specified index of an icon in the file HICON hIconLarge = NULL; ExtractIconEx(pszLoadFile, 0, &hIconLarge, &hFileIcon, 1); if (hIconLarge) DestroyIcon(hIconLarge); } else { //TODO: Shell icons for registered files (cmd, bat, sh, pl, py, ...) } if (hFileIcon) { int iIconIdxAdm = -1; iIconIdx = ImageList_ReplaceIcon(mh_TabIcons, -1, hFileIcon); TabIconCache NewIcon = {lstrdup(asIconDescr), false, iIconIdx}; m_Icons.push_back(NewIcon); HIMAGELIST hAdmList = ImageList_Merge(mh_TabIcons, iIconIdx, mh_TabIcons, mn_AdminIcon+2, 0,0); if (hAdmList) { HICON hNewIcon = ImageList_GetIcon(hAdmList, 0, ILD_TRANSPARENT); if (hNewIcon) { iIconIdxAdm = ImageList_ReplaceIcon(mh_TabIcons, -1, hNewIcon); DestroyIcon(hNewIcon); TabIconCache AdmIcon = {lstrdup(asIconDescr), true, iIconIdxAdm}; m_Icons.push_back(AdmIcon); if (bAdmin && (iIconIdxAdm > 0)) { iIconIdx = iIconIdxAdm; } } } //TODO: bAdmin!!! DestroyIcon(hFileIcon); } wrap: SafeFree(pszExpanded); return iIconIdx; }
static LRESULT CALLBACK TSButtonWndProc(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam) { MButtonCtrl* bct = (MButtonCtrl *)GetWindowLongPtr(hwndDlg, 0); switch (msg) { case WM_NCCREATE: { SetWindowLongPtr(hwndDlg, GWL_STYLE, GetWindowLongPtr(hwndDlg, GWL_STYLE) | BS_OWNERDRAW); bct = (MButtonCtrl *)malloc(sizeof(MButtonCtrl)); if (bct == NULL) return FALSE; ZeroMemory(bct, sizeof(MButtonCtrl)); bct->hwnd = hwndDlg; bct->stateId = PBS_NORMAL; bct->hFont = (HFONT)GetStockObject(DEFAULT_GUI_FONT); LoadTheme(bct); SetWindowLongPtr(hwndDlg, 0, (LONG_PTR)bct); if (((CREATESTRUCT *)lParam)->lpszName) SetWindowText(hwndDlg, ((CREATESTRUCT *)lParam)->lpszName); return TRUE; } case WM_DESTROY: { if (bct) { EnterCriticalSection(&csTips); if (hwndToolTips) { TOOLINFO ti; ZeroMemory(&ti, sizeof(ti)); ti.cbSize = sizeof(ti); ti.uFlags = TTF_IDISHWND; ti.hwnd = bct->hwnd; ti.uId = (UINT_PTR)bct->hwnd; if (SendMessage(hwndToolTips, TTM_GETTOOLINFO, 0, (LPARAM)&ti)) { SendMessage(hwndToolTips, TTM_DELTOOL, 0, (LPARAM)&ti); } if (SendMessage(hwndToolTips, TTM_GETTOOLCOUNT, 0, (LPARAM)&ti) == 0) { DestroyWindow(hwndToolTips); hwndToolTips = NULL; } } if (bct->hIconPrivate) DestroyIcon(bct->hIconPrivate); LeaveCriticalSection(&csTips); DestroyTheme(bct); } break; // DONT! fall thru } case WM_NCDESTROY: free(bct); SetWindowLongPtr(hwndDlg, 0, (LONG_PTR)NULL); break; case WM_SETTEXT: { bct->cHot = 0; if ((TCHAR *)lParam) { TCHAR *tmp = (TCHAR *)lParam; while (*tmp) { if (*tmp == (TCHAR)'&' && *(tmp + 1)) { bct->cHot = _totlower(*(tmp + 1)); break; } tmp++; } InvalidateRect(bct->hwnd, NULL, TRUE); } break; } case WM_KEYUP: if (bct->stateId != PBS_DISABLED && wParam == VK_SPACE && !(GetKeyState(VK_CONTROL) & 0x8000) && !(GetKeyState(VK_SHIFT) & 0x8000)) { if (bct->pushBtn) { if (bct->pbState) bct->pbState = 0; else bct->pbState = 1; InvalidateRect(bct->hwnd, NULL, TRUE); } SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(GetDlgCtrlID(hwndDlg), BN_CLICKED), (LPARAM)hwndDlg); return 0; } break; case WM_SYSKEYUP: if (bct->stateId != PBS_DISABLED && bct->cHot && bct->cHot == tolower((int)wParam)) { if (bct->pushBtn) { if (bct->pbState) bct->pbState = 0; else bct->pbState = 1; InvalidateRect(bct->hwnd, NULL, TRUE); } SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(GetDlgCtrlID(hwndDlg), BN_CLICKED), (LPARAM)hwndDlg); return 0; } break; case WM_THEMECHANGED: { // themed changed, reload theme object if (bct->bThemed) LoadTheme(bct); InvalidateRect(bct->hwnd, NULL, TRUE); // repaint it break; } case WM_SETFONT: { // remember the font so we can use it later bct->hFont = (HFONT)wParam; // maybe we should redraw? break; } case WM_NCPAINT: return(0); case WM_PAINT: { PAINTSTRUCT ps; HDC hdcPaint; hdcPaint = BeginPaint(hwndDlg, &ps); if (hdcPaint) { if(bct->sitem) bct->sitem->RenderThis(hdcPaint); else PaintWorker(bct, hdcPaint); EndPaint(hwndDlg, &ps); } return(0); } case BM_SETIMAGE: if (wParam == IMAGE_ICON) { ICONINFO ii; BITMAP bm; if (bct->hIconPrivate) DestroyIcon(bct->hIconPrivate); GetIconInfo((HICON)lParam, &ii); GetObject(ii.hbmColor, sizeof(bm), &bm); if (bm.bmWidth != PluginConfig.m_smcxicon || bm.bmHeight != PluginConfig.m_smcyicon) { HIMAGELIST hImageList; hImageList = ImageList_Create(PluginConfig.m_smcxicon, PluginConfig.m_smcyicon, PluginConfig.m_bIsXP ? ILC_COLOR32 | ILC_MASK : ILC_COLOR16 | ILC_MASK, 1, 0); ImageList_AddIcon(hImageList, (HICON)lParam); bct->hIconPrivate = ImageList_GetIcon(hImageList, 0, ILD_NORMAL); ImageList_RemoveAll(hImageList); ImageList_Destroy(hImageList); bct->hIcon = 0; } else { bct->hIcon = (HICON)lParam; bct->hIconPrivate = 0; } DeleteObject(ii.hbmMask); DeleteObject(ii.hbmColor); bct->hBitmap = NULL; InvalidateRect(bct->hwnd, NULL, TRUE); } else if (wParam == IMAGE_BITMAP) { bct->hBitmap = (HBITMAP)lParam; if (bct->hIconPrivate) DestroyIcon(bct->hIconPrivate); bct->hIcon = bct->hIconPrivate = NULL; InvalidateRect(bct->hwnd, NULL, TRUE); } break; case BM_SETCHECK: if (!bct->pushBtn) break; if (wParam == BST_CHECKED) { bct->pbState = 1; bct->stateId = PBS_PRESSED; } else if (wParam == BST_UNCHECKED) { bct->pbState = 0; bct->stateId = PBS_NORMAL; } InvalidateRect(bct->hwnd, NULL, TRUE); break; case BM_GETCHECK: if (bct->pushBtn) { return bct->pbState ? BST_CHECKED : BST_UNCHECKED; } return 0; case BUTTONSETARROW: // turn arrow on/off bct->arrow = (HICON)wParam; InvalidateRect(bct->hwnd, NULL, TRUE); break; case BUTTONSETDEFAULT: bct->defbutton = wParam ? 1 : 0; InvalidateRect(bct->hwnd, NULL, TRUE); break; case BUTTONSETASPUSHBTN: bct->pushBtn = 1; InvalidateRect(bct->hwnd, NULL, TRUE); break; case BUTTONSETASFLATBTN: bct->flatBtn = lParam == 0 ? 1 : 0; InvalidateRect(bct->hwnd, NULL, TRUE); break; case BUTTONSETASFLATBTN + 10: bct->bThemed = lParam ? TRUE : FALSE; break; case BUTTONSETASFLATBTN + 11: bct->dimmed = lParam ? TRUE : FALSE; break; case BUTTONSETASFLATBTN + 12: bct->pContainer = (struct TContainerData *)lParam; break; case BUTTONSETASFLATBTN + 13: bct->bTitleButton = TRUE; break; case BUTTONSETASFLATBTN + 14: bct->stateId = (wParam) ? PBS_NORMAL : PBS_DISABLED; InvalidateRect(bct->hwnd, NULL, FALSE); break; case BUTTONSETASFLATBTN + 15: return bct->stateId; case BUTTONSETASTOOLBARBUTTON: bct->bToolbarButton = lParam; break; case BUTTONSETASSIDEBARBUTTON: bct->sitem = reinterpret_cast<CSideBarButton *>(lParam); break; case BUTTONSETOVERLAYICON: bct->overlay = (HICON)lParam; break; case BUTTONADDTOOLTIP: { TOOLINFO ti; if (!(char*)wParam) break; EnterCriticalSection(&csTips); if (!hwndToolTips) { hwndToolTips = CreateWindowEx(WS_EX_TOPMOST, TOOLTIPS_CLASS, _T(""), WS_POPUP, 0, 0, 0, 0, NULL, NULL, GetModuleHandle(NULL), NULL); } ZeroMemory(&ti, sizeof(ti)); ti.cbSize = sizeof(ti); ti.uFlags = TTF_IDISHWND; ti.hwnd = bct->hwnd; ti.uId = (UINT_PTR)bct->hwnd; if (SendMessage(hwndToolTips, TTM_GETTOOLINFO, 0, (LPARAM)&ti)) { SendMessage(hwndToolTips, TTM_DELTOOL, 0, (LPARAM)&ti); } ti.uFlags = TTF_IDISHWND | TTF_SUBCLASS; ti.uId = (UINT_PTR)bct->hwnd; ti.lpszText = (TCHAR *)wParam; SendMessage(hwndToolTips, TTM_ADDTOOL, 0, (LPARAM)&ti); SendMessage(hwndToolTips, TTM_SETMAXTIPWIDTH, 0, 300); LeaveCriticalSection(&csTips); break; } case WM_SETFOCUS: // set keybord focus and redraw bct->focus = 1; InvalidateRect(bct->hwnd, NULL, TRUE); break; case WM_KILLFOCUS: // kill focus and redraw bct->focus = 0; InvalidateRect(bct->hwnd, NULL, TRUE); break; case WM_ENABLE: { // windows tells us to enable/disable bct->stateId = wParam ? PBS_NORMAL : PBS_DISABLED; InvalidateRect(bct->hwnd, NULL, TRUE); break; } case WM_MOUSELEAVE: { // faked by the WM_TIMER if (bct->stateId != PBS_DISABLED) { // don't change states if disabled bct->stateId = PBS_NORMAL; InvalidateRect(bct->hwnd, NULL, TRUE); } break; } case WM_CONTEXTMENU: if(bct->sitem) bct->sitem->invokeContextMenu(); break; case WM_MBUTTONUP: if(bct->sitem) { if(bct->sitem->getDat()) SendMessage(bct->sitem->getDat()->hwnd, WM_CLOSE, 1, 0); } break; case WM_LBUTTONDOWN: { RECT rc; if(bct->sitem) { if(bct->sitem->testCloseButton() != -1) return(TRUE); bct->stateId = PBS_PRESSED; InvalidateRect(bct->hwnd, NULL, TRUE); bct->sitem->activateSession(); } if (bct->arrow) { GetClientRect(bct->hwnd, &rc); if (LOWORD(lParam) < rc.right - 12 && bct->stateId != PBS_DISABLED) bct->stateId = PBS_PRESSED; else if(LOWORD(lParam) > rc.right - 12) { if(GetDlgCtrlID(hwndDlg) == IDOK || bct->stateId != PBS_DISABLED) { WORD w = (WORD)((int)bct->arrow & 0x0000ffff); SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(w, BN_CLICKED), (LPARAM)hwndDlg); } } InvalidateRect(bct->hwnd, NULL, TRUE); } else if (bct->stateId != PBS_DISABLED) { bct->stateId = PBS_PRESSED; InvalidateRect(bct->hwnd, NULL, TRUE); } break; } case WM_LBUTTONUP: { int showClick = 0; if (bct->sitem) { if(bct->sitem->testCloseButton() != -1) { SendMessage(bct->sitem->getDat()->hwnd, WM_CLOSE, 1, 0); return(TRUE); } } if (bct->pushBtn) { if (bct->pbState) bct->pbState = 0; else bct->pbState = 1; } if (bct->stateId != PBS_DISABLED) { // don't change states if disabled if(bct->stateId == PBS_PRESSED) showClick = 1; if (msg == WM_LBUTTONUP) bct->stateId = PBS_HOT; else bct->stateId = PBS_NORMAL; InvalidateRect(bct->hwnd, NULL, TRUE); } if(showClick) SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(GetDlgCtrlID(hwndDlg), BN_CLICKED), (LPARAM)hwndDlg); break; } case WM_MOUSEMOVE: if (bct->stateId == PBS_NORMAL) { bct->stateId = PBS_HOT; InvalidateRect(bct->hwnd, NULL, TRUE); } else if (bct->arrow && bct->stateId == PBS_HOT) { InvalidateRect(bct->hwnd, NULL, TRUE); } // Call timer, used to start cheesy TrackMouseEvent faker SetTimer(hwndDlg, BUTTON_POLLID, BUTTON_POLLDELAY, NULL); if(bct->sitem) { if(bct->sitem->testCloseButton() != -1) { if(bct->sitem->m_sideBar->getHoveredClose() != bct->sitem) { bct->sitem->m_sideBar->setHoveredClose(bct->sitem); InvalidateRect(hwndDlg, 0, FALSE); } } else { bct->sitem->m_sideBar->setHoveredClose(0); InvalidateRect(hwndDlg, 0, FALSE); } } break; case WM_TIMER: { // use a timer to check if they have did a mouseout if (wParam == BUTTON_POLLID) { RECT rc; POINT pt; GetWindowRect(hwndDlg, &rc); GetCursorPos(&pt); if (!PtInRect(&rc, pt)) { // mouse must be gone, trigger mouse leave PostMessage(hwndDlg, WM_MOUSELEAVE, 0, 0L); KillTimer(hwndDlg, BUTTON_POLLID); if(bct->sitem) { bct->sitem->m_sideBar->setHoveredClose(0); InvalidateRect(hwndDlg, 0, FALSE); } } } break; } case WM_ERASEBKGND: return(1); } return DefWindowProc(hwndDlg, msg, wParam, lParam); }
/** * name: Icon * class: CPsTreeItem * desc: load the icon, add to icolib if required and add to imagelist of treeview * params: hIml - treeview's imagelist to add the icon to * odp - pointer to OPTIONSDIALOGPAGE providing the information about the icon to load * hDefaultIcon - default icon to use * return: nothing **/ int CPsTreeItem::Icon(HIMAGELIST hIml, OPTIONSDIALOGPAGE *odp, BYTE bInitIconsOnly) { // check parameter if (!_pszName || !odp) return 1; // load the icon if no icolib is installed or creating the required settingname failed LPCSTR pszIconName = IconKey(); // use icolib to handle icons HICON hIcon = IcoLib_GetIcon(pszIconName); if (!hIcon) { bool bNeedFree = false; SKINICONDESC sid = { 0 }; sid.flags = SIDF_ALL_TCHAR; sid.pszName = (LPSTR)pszIconName; sid.description.t = _ptszLabel; sid.section.t = LPGENT(SECT_TREE); // the item to insert brings along an icon? if (odp->flags & ODPF_ICON) { // is it uinfoex item? if (odp->hInstance == ghInst) { // the pszGroup holds the iconfile for items added by uinfoex sid.defaultFile.t = odp->ptszGroup; // icon library exists? if (sid.defaultFile.t) sid.iDefaultIndex = (INT_PTR)odp->hIcon; // no valid icon library else { bNeedFree = true; sid.hDefaultIcon = ImageList_GetIcon(hIml, 0, ILD_NORMAL); sid.iDefaultIndex = -1; } } // default icon is delivered by the page to add else { if (odp->hIcon) sid.hDefaultIcon = odp->hIcon; else sid.hDefaultIcon = ImageList_GetIcon(hIml, 0, ILD_NORMAL), bNeedFree = true; sid.iDefaultIndex = -1; } } // no icon to add, use default else { sid.iDefaultIndex = -1; sid.hDefaultIcon = ProtoIcon(); if (!sid.hDefaultIcon) sid.hDefaultIcon = ImageList_GetIcon(hIml, 0, ILD_NORMAL), bNeedFree = true; } // add file to icolib IcoLib_AddIcon(&sid); if (!bInitIconsOnly) hIcon = IcoLib_GetIcon(pszIconName); if (bNeedFree) DestroyIcon(sid.hDefaultIcon); } if (!bInitIconsOnly && hIml) { // set custom icon to image list if (hIcon) return ((_iImage = ImageList_AddIcon(hIml, hIcon)) == -1); _iImage = 0; } else _iImage = -1; return 0; }
int CIconList::CreateTabIconInt(LPCWSTR asIconDescr, bool bAdmin, LPCWSTR asWorkDir) { wchar_t* pszExpanded = ExpandEnvStr(asIconDescr); // Need to be created! int iIconIdx = -1; HICON hFileIcon = NULL; wchar_t szTemp[MAX_PATH]; LPCWSTR pszLoadFile = pszExpanded ? pszExpanded : asIconDescr; LPCWSTR lpszExt = (wchar_t*)PointToExt(pszLoadFile); bool bDirChanged = false; if (asWorkDir && *asWorkDir) { // Executable (or icon) file may be not availbale by %PATH%, let "cd" to it... bDirChanged = gpConEmu->ChangeWorkDir(asWorkDir); } if (!lpszExt) { LPWSTR pszFile = NULL; if (SearchPath(NULL, pszLoadFile, L".exe", countof(szTemp), szTemp, &pszFile)) { pszLoadFile = szTemp; lpszExt = (wchar_t*)PointToExt(pszLoadFile); } if (!lpszExt) goto wrap; } if (lstrcmpi(lpszExt, L".ico") == 0) { hFileIcon = (HICON)LoadImage(0, pszLoadFile, IMAGE_ICON, GetSystemMetrics(SM_CXSMICON), GetSystemMetrics(SM_CYSMICON), LR_DEFAULTCOLOR|LR_LOADFROMFILE); } else if ((lstrcmpi(lpszExt, L".exe") == 0) || (lstrcmpi(lpszExt, L".dll") == 0)) { //TODO: May be specified index of an icon in the file HICON hIconLarge = NULL; ExtractIconEx(pszLoadFile, 0, &hIconLarge, &hFileIcon, 1); if (hIconLarge) DestroyIcon(hIconLarge); } else { //TODO: Shell icons for registered files (cmd, bat, sh, pl, py, ...) } if (hFileIcon) { int iIconIdxAdm = -1; iIconIdx = ImageList_ReplaceIcon(mh_TabIcons, -1, hFileIcon); TabIconCache NewIcon = {lstrdup(asIconDescr), false, iIconIdx}; m_Icons.push_back(NewIcon); HIMAGELIST hAdmList = ImageList_Merge(mh_TabIcons, iIconIdx, mh_TabIcons, mn_AdminIcon+2, 0,0); if (hAdmList) { HICON hNewIcon = ImageList_GetIcon(hAdmList, 0, ILD_TRANSPARENT); if (hNewIcon) { iIconIdxAdm = ImageList_ReplaceIcon(mh_TabIcons, -1, hNewIcon); DestroyIcon(hNewIcon); TabIconCache AdmIcon = {lstrdup(asIconDescr), true, iIconIdxAdm}; m_Icons.push_back(AdmIcon); if (bAdmin && (iIconIdxAdm > 0)) { iIconIdx = iIconIdxAdm; } } } //TODO: bAdmin!!! DestroyIcon(hFileIcon); } wrap: if (bDirChanged) { gpConEmu->ChangeWorkDir(NULL); } SafeFree(pszExpanded); return iIconIdx; }
INT_PTR CALLBACK DlgProcFiltering(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam) { static HANDLE hItemAll; switch (msg) { case WM_INITDIALOG: { TranslateDialogDefault(hwndDlg); HIMAGELIST hImageList = ImageList_Create(GetSystemMetrics(SM_CXSMICON), GetSystemMetrics(SM_CYSMICON), IsWinVerXPPlus() ? ILC_COLOR32 : ILC_COLOR16 | ILC_MASK, 3, 3); ImageList_AddIcon(hImageList, LoadIcon(hInst,MAKEINTRESOURCE(IDI_SOUND))); SendDlgItemMessage(hwndDlg,IDC_SOUNDICON,STM_SETICON, (WPARAM)ImageList_GetIcon(hImageList, EXTRA_IMAGE_SOUND, ILD_NORMAL), 0); ImageList_AddIcon(hImageList, LoadIcon(hInst, MAKEINTRESOURCE(IDI_POPUP))); SendDlgItemMessage(hwndDlg, IDC_POPUPICON, STM_SETICON, (WPARAM)ImageList_GetIcon(hImageList, EXTRA_IMAGE_POPUP, ILD_NORMAL), 0); ImageList_AddIcon(hImageList, LoadIcon(hInst,MAKEINTRESOURCE(IDI_XSTATUS))); SendDlgItemMessage(hwndDlg, IDC_XSTATUSICON, STM_SETICON, (WPARAM)ImageList_GetIcon(hImageList, EXTRA_IMAGE_XSTATUS, ILD_NORMAL), 0); ImageList_AddIcon(hImageList, LoadIcon(hInst,MAKEINTRESOURCE(IDI_LOGGING))); SendDlgItemMessage(hwndDlg, IDC_LOGGINGICON, STM_SETICON, (WPARAM)ImageList_GetIcon(hImageList, EXTRA_IMAGE_LOGGING, ILD_NORMAL), 0); ImageList_AddIcon(hImageList, LoadIcon(hInst,MAKEINTRESOURCE(IDI_DISABLEALL))); SendDlgItemMessage(hwndDlg, IDC_DISABLEALLICON, STM_SETICON, (WPARAM)ImageList_GetIcon(hImageList, EXTRA_IMAGE_DISABLEALL, ILD_NORMAL), 0); ImageList_AddIcon(hImageList, LoadIcon(hInst,MAKEINTRESOURCE(IDI_ENABLEALL))); SendDlgItemMessage(hwndDlg, IDC_ENABLEALLICON, STM_SETICON, (WPARAM)ImageList_GetIcon(hImageList, EXTRA_IMAGE_ENABLEALL, ILD_NORMAL), 0); ImageList_AddIcon(hImageList, LoadSkinnedIcon(SKINICON_OTHER_SMALLDOT)); SendDlgItemMessage(hwndDlg, IDC_INDSNDLIST, CLM_SETEXTRAIMAGELIST, 0, (LPARAM)hImageList); SendDlgItemMessage(hwndDlg, IDC_INDSNDLIST, CLM_SETEXTRACOLUMNS, 6, 0); HWND hList = GetDlgItem(hwndDlg, IDC_INDSNDLIST); ResetListOptions(hList); CLCINFOITEM cii = {0}; cii.cbSize = sizeof(cii); cii.flags = CLCIIF_GROUPFONT; cii.pszText = TranslateT("** All contacts **"); hItemAll = (HANDLE)SendDlgItemMessage(hwndDlg, IDC_INDSNDLIST, CLM_ADDINFOITEM, 0, (LPARAM)&cii); return TRUE; } case WM_SETFOCUS: { SetFocus(GetDlgItem(hwndDlg, IDC_INDSNDLIST)); break; } case WM_NOTIFY: { HWND hList = GetDlgItem(hwndDlg, IDC_INDSNDLIST); switch(((LPNMHDR)lParam)->idFrom) { case IDC_INDSNDLIST: switch (((LPNMHDR)lParam)->code) { case CLN_NEWCONTACT: case CLN_LISTREBUILT: SetAllContactsIcons(hList); //fall through case CLN_CONTACTMOVED: SetGroupsIcons(hList, (HANDLE)SendMessage(hList, CLM_GETNEXTITEM, CLGN_ROOT, 0), hItemAll, NULL); break; case CLN_OPTIONSCHANGED: ResetListOptions(hList); break; case NM_CLICK: { NMCLISTCONTROL *nm = (NMCLISTCONTROL*)lParam; DWORD hitFlags; // Make sure we have an extra column if (nm->iColumn == -1) break; // Find clicked item HANDLE hItem = (HANDLE)SendMessage(hList, CLM_HITTEST, (WPARAM)&hitFlags, MAKELPARAM(nm->pt.x, nm->pt.y)); if (hItem == NULL) break; if(!(hitFlags & CLCHT_ONITEMEXTRA)) break; int itemType = SendMessage(hList, CLM_GETITEMTYPE, (WPARAM)hItem, 0); // Get image in clicked column int image = GetExtraImage(hList, hItem, nm->iColumn); if (image == EXTRA_IMAGE_DOT) image = nm->iColumn; else if (image >= EXTRA_IMAGE_SOUND && image <= EXTRA_IMAGE_LOGGING) image = EXTRA_IMAGE_DOT; // Get item type (contact, group, etc...) if (itemType == CLCIT_CONTACT) { if (image == EXTRA_IMAGE_DISABLEALL) { for (int i = 0; i < 4; i++) SetExtraImage(hList, hItem, i, EXTRA_IMAGE_DOT); } else if (image == EXTRA_IMAGE_ENABLEALL) { for (int i = 0; i < 4; i++) SetExtraImage(hList, hItem, i, i); } else { SetExtraImage(hList, hItem, nm->iColumn, image); } } else if (itemType == CLCIT_INFO || itemType == CLCIT_GROUP) { if (itemType == CLCIT_GROUP) hItem = (HANDLE)SendMessage(hList, CLM_GETNEXTITEM, CLGN_CHILD, (LPARAM)hItem); if (hItem) { if (image == EXTRA_IMAGE_DISABLEALL) { for (int i = 0; i < 4; i++) SetAllChildrenIcons(hList, hItem, i, EXTRA_IMAGE_DOT); } else if (image == EXTRA_IMAGE_ENABLEALL) { for (int i = 0; i < 4; i++) SetAllChildrenIcons(hList, hItem, i, i); } else { SetAllChildrenIcons(hList, hItem, nm->iColumn, image); } } } // Update the all/none icons SetGroupsIcons(hList, (HANDLE)SendMessage(hList, CLM_GETNEXTITEM, CLGN_ROOT, 0), hItemAll, NULL); // Activate Apply button SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0); break; } } break; case 0: switch (((LPNMHDR)lParam)->code) { case PSN_APPLY: { HANDLE hContact = (HANDLE)CallService(MS_DB_CONTACT_FINDFIRST, 0, 0); do { HANDLE hItem = (HANDLE)SendMessage(hList, CLM_FINDCONTACT, (WPARAM)hContact, 0); if (hItem) { if (GetExtraImage(hList, hItem, EXTRA_IMAGE_SOUND) == EXTRA_IMAGE_SOUND) DBDeleteContactSetting(hContact, MODULE, "EnableSounds"); else DBWriteContactSettingByte(hContact, MODULE, "EnableSounds", 0); if (GetExtraImage(hList, hItem, EXTRA_IMAGE_POPUP) == EXTRA_IMAGE_POPUP) DBDeleteContactSetting(hContact, MODULE, "EnablePopups"); else DBWriteContactSettingByte(hContact, MODULE, "EnablePopups", 0); if(GetExtraImage(hList, hItem, EXTRA_IMAGE_XSTATUS) == EXTRA_IMAGE_XSTATUS) DBDeleteContactSetting(hContact, MODULE, "EnableXStatusNotify"); else DBWriteContactSettingByte(hContact, MODULE, "EnableXStatusNotify", 0); if (GetExtraImage(hList, hItem, EXTRA_IMAGE_LOGGING) == EXTRA_IMAGE_LOGGING) DBDeleteContactSetting(hContact, MODULE, "EnableLogging"); else DBWriteContactSettingByte(hContact, MODULE, "EnableLogging", 0); } } while(hContact = (HANDLE)CallService(MS_DB_CONTACT_FINDNEXT, (WPARAM)hContact, 0)); return TRUE; } } break; } break; } case WM_DESTROY: { HIMAGELIST hImageList = (HIMAGELIST)SendMessage(GetDlgItem(hwndDlg, IDC_INDSNDLIST), CLM_GETEXTRAIMAGELIST, 0, 0); for (int i = 0; i < ImageList_GetImageCount(hImageList); i++) DestroyIcon(ImageList_GetIcon(hImageList, i, ILD_NORMAL)); ImageList_Destroy(hImageList); break; } } return FALSE; }
static LRESULT CALLBACK TollbarButtonProc(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam) { TBBUTTONDATA *lpSBData = (TBBUTTONDATA *) GetWindowLongPtr(hwndDlg, 0); switch (msg) { case WM_NCCREATE: { SetWindowLong(hwndDlg, GWL_STYLE, GetWindowLong(hwndDlg, GWL_STYLE) | BS_OWNERDRAW); lpSBData = (TBBUTTONDATA *)malloc(sizeof(TBBUTTONDATA)); if (lpSBData == NULL) return FALSE; memset(lpSBData,0,sizeof(TBBUTTONDATA)); //I prefer memset to guarantee zeros lpSBData->hWnd = hwndDlg; lpSBData->nStateId = PBS_NORMAL; lpSBData->fFocused = FALSE; lpSBData->hFont = (HFONT)GetStockObject(DEFAULT_GUI_FONT); lpSBData->hIconPrivate = NULL; lpSBData->cHot = '\0'; lpSBData->szText[0] = '\0'; lpSBData->szButtonID[0] = '?'; lpSBData->szButtonID[1] = '\0'; lpSBData->pushBtn = FALSE; lpSBData->pbState = 0; lpSBData->fSendOnDown = FALSE; lpSBData->fHotMark = FALSE; lpSBData->nFontID = -1; SetWindowLongPtr(hwndDlg, 0, (LONG_PTR) lpSBData); if (((CREATESTRUCTA *) lParam)->lpszName) SetWindowText(hwndDlg, ((CREATESTRUCT *) lParam)->lpszName); lpSBData->hThemeButton = xpt_AddThemeHandle(lpSBData->hWnd, L"BUTTON"); lpSBData->hThemeToolbar = xpt_AddThemeHandle(lpSBData->hWnd, L"TOOLBAR"); WindowList_Add(hButtonWindowList, hwndDlg, NULL); return TRUE; } case WM_DESTROY: { /* #ifdef _DEBUG if (GetWindowLong(hwndButton, GWL_USERDATA)) DebugBreak(); #endif */ xpt_FreeThemeForWindow(hwndDlg); WindowList_Remove(hButtonWindowList, hwndDlg); if (lpSBData) { if (hwndToolTips) { TOOLINFO ti; ZeroMemory(&ti, sizeof(ti)); ti.cbSize = sizeof(ti); ti.uFlags = TTF_IDISHWND; ti.hwnd = lpSBData->hWnd; ti.uId = (UINT_PTR) lpSBData->hWnd; if (SendMessage(hwndToolTips, TTM_GETTOOLINFO, 0, (LPARAM) &ti)) { SendMessage(hwndToolTips, TTM_DELTOOL, 0, (LPARAM) &ti); } if (SendMessage(hwndToolTips, TTM_GETTOOLCOUNT, 0, (LPARAM) &ti) == 0) { DestroyWindow(hwndToolTips); hwndToolTips = NULL; } } if (lpSBData->hIconPrivate) DestroyIcon(lpSBData->hIconPrivate); free(lpSBData); // lpSBData was malloced by native malloc } SetWindowLong(hwndDlg, 0, (LONG) NULL); break; // DONT! fall thru } case WM_SETTEXT: { lpSBData->cHot = 0; if ((TCHAR*) lParam) { TCHAR *tmp = (TCHAR *) lParam; while (*tmp) { if (*tmp == '&' && *(tmp + 1)) { lpSBData->cHot = (char)tolower(*(tmp + 1)); break; } tmp++; } InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); lstrcpyn(lpSBData->szText, (TCHAR *)lParam, SIZEOF(lpSBData->szText)-1); lpSBData->szText[SIZEOF(lpSBData->szText)-1] = '\0'; } break; } case WM_SYSKEYUP: if (lpSBData->nStateId != PBS_DISABLED && lpSBData->cHot && lpSBData->cHot == tolower((int) wParam)) { if (lpSBData->pushBtn) { if (lpSBData->pbState) lpSBData->pbState = 0; else lpSBData->pbState = 1; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); } if(!lpSBData->fSendOnDown) SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(GetDlgCtrlID(hwndDlg), BN_CLICKED), (LPARAM) hwndDlg); return 0; } break; case WM_SETFONT: { // remember the font so we can use it later lpSBData->hFont = (HFONT) wParam; // maybe we should redraw? lpSBData->nFontID = (int) lParam - 1; break; } case BUTTONSETSENDONDOWN: { lpSBData->fSendOnDown = (BOOL) lParam; break; } case BUTTONSETMARGINS: { if (lParam) lpSBData->rcMargins=*(RECT*)lParam; else { RECT nillRect={0}; lpSBData->rcMargins=nillRect; } return 0; } case BUTTONSETID: { lstrcpynA(lpSBData->szButtonID, (char *)lParam, SIZEOF(lpSBData->szButtonID)-1); lpSBData->szButtonID[SIZEOF(lpSBData->szButtonID)-1] = '\0'; return 0; } case BUTTONDRAWINPARENT: { if (IsWindowVisible(hwndDlg)) PaintWorker(lpSBData, (HDC) wParam, (POINT*) lParam); return 0; } case WM_NCPAINT: case WM_PAINT: { PAINTSTRUCT ps; HDC hdcPaint; if (g_CluiData.fDisableSkinEngine) { hdcPaint = BeginPaint(hwndDlg, &ps); if (hdcPaint) { PaintWorker(lpSBData, hdcPaint, NULL); EndPaint(hwndDlg, &ps); } } ValidateRect(hwndDlg,NULL); return 0; } case BUTTONADDTOOLTIP: { TOOLINFO ti; if (!(char*) wParam) break; if (!hwndToolTips) { hwndToolTips = CreateWindowEx(WS_EX_TOPMOST, TOOLTIPS_CLASS, _T(""), WS_POPUP, 0, 0, 0, 0, NULL, NULL, GetModuleHandle(NULL), NULL); SetWindowPos(hwndToolTips, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOSIZE | SWP_NOMOVE); } ZeroMemory(&ti, sizeof(ti)); ti.cbSize = sizeof(ti); ti.uFlags = TTF_IDISHWND; ti.hwnd = lpSBData->hWnd; ti.uId = (UINT_PTR) lpSBData->hWnd; if (SendMessage(hwndToolTips, TTM_GETTOOLINFO, 0, (LPARAM) &ti)) { SendMessage(hwndToolTips, TTM_DELTOOL, 0, (LPARAM) &ti); } ti.uFlags = TTF_IDISHWND | TTF_SUBCLASS; ti.uId = (UINT_PTR) lpSBData->hWnd; ti.lpszText = (TCHAR *) wParam; SendMessage(hwndToolTips, TTM_ADDTOOL, 0, (LPARAM) &ti); break; } case BUTTONSETASPUSHBTN: { if (lParam==0) lpSBData->pushBtn=1; else { lpSBData->pushBtn=wParam; lpSBData->pbState = (lParam&2) ? TRUE : FALSE; } return 0; } case WM_SETFOCUS: { // set keyboard focus and redraw lpSBData->fFocused = TRUE; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); break; } case WM_KILLFOCUS: { // kill focus and redraw lpSBData->fFocused = FALSE; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); break; } case WM_WINDOWPOSCHANGED: InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); break; case WM_ENABLE: // windows tells us to enable/disable { lpSBData->nStateId = wParam ? PBS_NORMAL : PBS_DISABLED; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); break; } /*case WM_MOUSELEAVE: { // faked by the WM_TIMER if (lpSBData->nStateId != PBS_DISABLED) { // don't change states if disabled lpSBData->nStateId = PBS_NORMAL; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); } break; } */ case WM_CAPTURECHANGED: { if ( (HWND)lParam != lpSBData->hWnd && lpSBData->nStateId != PBS_DISABLED) { // don't change states if disabled lpSBData->nStateId = PBS_NORMAL; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); } break; } case WM_LBUTTONDOWN: { int xPos=( ( int )( short ) LOWORD( lParam ) ); int yPos=( ( int )( short ) HIWORD( lParam ) ); POINT ptMouse = { xPos, yPos }; RECT rcClient; GetClientRect( lpSBData->hWnd, &rcClient ); if ( !PtInRect( &rcClient, ptMouse ) ) { lpSBData->fHotMark = FALSE; ReleaseCapture(); break; } if (lpSBData->nStateId != PBS_DISABLED && lpSBData->nStateId != PBS_PRESSED) { lpSBData->nStateId = PBS_PRESSED; lpSBData->fHotMark = TRUE; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); if(lpSBData->fSendOnDown) { SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(GetDlgCtrlID(hwndDlg), BN_CLICKED), (LPARAM) hwndDlg); lpSBData->nStateId = PBS_NORMAL; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); } } SetCapture( lpSBData->hWnd ); break; } case WM_LBUTTONUP: if ( GetCapture() == lpSBData->hWnd ) { int xPos=( ( int )( short ) LOWORD( lParam ) ); int yPos=( ( int )( short ) HIWORD( lParam ) ); POINT ptMouse = { xPos, yPos }; RECT rcClient; GetClientRect( lpSBData->hWnd, &rcClient ); if ( !PtInRect( &rcClient, ptMouse ) ) { lpSBData->fHotMark = FALSE; ReleaseCapture(); break; } if (lpSBData->pushBtn) { if (lpSBData->pbState) lpSBData->pbState = FALSE; else lpSBData->pbState = TRUE; } if (lpSBData->nStateId != PBS_DISABLED) { // don't change states if disabled if (msg == WM_LBUTTONUP) lpSBData->nStateId = PBS_HOT; else lpSBData->nStateId = PBS_NORMAL; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); } if(!lpSBData->fSendOnDown && lpSBData->fHotMark) SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(GetDlgCtrlID(hwndDlg), BN_CLICKED), (LPARAM) hwndDlg); lpSBData->fHotMark = FALSE; break; } case WM_MOUSEMOVE: { RECT rc; POINT pt; BOOL bPressed = (wParam & MK_LBUTTON) != 0; if ( bPressed && !lpSBData->fHotMark ) break; GetWindowRect(hwndDlg, &rc); GetCursorPos(&pt); BOOL inClient = PtInRect(&rc, pt); if ( inClient ) { SetCapture( lpSBData->hWnd ); if ( lpSBData->nStateId == PBS_NORMAL ) { lpSBData->nStateId = PBS_HOT; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); } } if ( !inClient && lpSBData->nStateId == PBS_PRESSED ) { lpSBData->nStateId = PBS_HOT; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); } else if ( inClient && lpSBData->nStateId == PBS_HOT && bPressed ) { if( lpSBData->fHotMark ) { lpSBData->nStateId = PBS_PRESSED; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); } } else if ( !inClient && !bPressed) { lpSBData->fHotMark = FALSE; ReleaseCapture(); } } // else { //KillTimer(hwndDlg, BUTTON_POLLID); //CLUI_SafeSetTimer(hwndDlg, BUTTON_POLLID, BUTTON_POLLDELAY, NULL); } // Call timer, used to start cheesy TrackMouseEvent faker break; case WM_NCHITTEST: { LRESULT lr = SendMessage(GetParent(hwndDlg), WM_NCHITTEST, wParam, lParam); if(lr == HTLEFT || lr == HTRIGHT || lr == HTBOTTOM || lr == HTTOP || lr == HTTOPLEFT || lr == HTTOPRIGHT || lr == HTBOTTOMLEFT || lr == HTBOTTOMRIGHT) return HTTRANSPARENT; break; } /*case WM_TIMER: // use a timer to check if they have did a mouse out { if (wParam == BUTTON_POLLID) { HWND hwnd=GetCapture(); if ( hwnd == lpSBData->hWnd ) { //KillTimer(hwndDlg, BUTTON_POLLID); break; } RECT rc; POINT pt; GetWindowRect(hwndDlg, &rc); GetCursorPos(&pt); BOOL bInside = ( PtInRect( &rc, pt ) && ( WindowFromPoint( pt ) == lpSBData->hWnd) ); if ( !bInside ) { // mouse must be gone, trigger mouse leave PostMessage(hwndDlg, WM_MOUSELEAVE, 0, 0L); KillTimer(hwndDlg, BUTTON_POLLID); } } break; } */ case WM_ERASEBKGND: { return 1; } case MBM_SETICOLIBHANDLE: { if (lpSBData->hIconPrivate) { DestroyIcon(lpSBData->hIconPrivate); lpSBData->hIconPrivate = 0; } lpSBData->hIcolibHandle=(HANDLE)lParam; if (lpSBData->hIcolibHandle) lpSBData->hIcon=(HICON)CallService(MS_SKIN2_GETICONBYHANDLE, 0 , (LPARAM) lpSBData->hIcolibHandle); else lpSBData->hIcon=NULL; return 1; } case MBM_REFRESHICOLIBICON: { if (lpSBData->hIconPrivate) { DestroyIcon(lpSBData->hIconPrivate); lpSBData->hIconPrivate = 0; } if (lpSBData->hIcolibHandle) lpSBData->hIcon=(HICON)CallService(MS_SKIN2_GETICONBYHANDLE, 0 , (LPARAM) lpSBData->hIcolibHandle); else lpSBData->hIcon=NULL; InvalidateRect(hwndDlg,NULL,TRUE); pcli->pfnInvalidateRect(GetParent(GetParent(hwndDlg)),NULL,TRUE); return 1; } case MBM_UPDATETRANSPARENTFLAG: { LONG flag=GetWindowLong(hwndDlg,GWL_EXSTYLE); LONG oldFlag=flag; if (lParam==2) lParam=(g_CluiData.fDisableSkinEngine)?0:1; flag&=~WS_EX_TRANSPARENT; if (lParam) flag|=WS_EX_TRANSPARENT; if (flag!=oldFlag) { SetWindowLong(hwndDlg,GWL_EXSTYLE,flag); RedrawWindow(hwndDlg,NULL,NULL,RDW_INVALIDATE|RDW_UPDATENOW); } return 0; } case BM_GETIMAGE: { if(wParam == IMAGE_ICON) return (LRESULT)(lpSBData->hIconPrivate ? lpSBData->hIconPrivate : lpSBData->hIcon); break; } case BM_SETIMAGE: { if(!lParam) break; if (wParam == IMAGE_ICON) { ICONINFO ii = {0}; BITMAP bm = {0}; if (lpSBData->hIconPrivate) { DestroyIcon(lpSBData->hIconPrivate); lpSBData->hIconPrivate = 0; } GetIconInfo((HICON) lParam, &ii); GetObject(ii.hbmColor, sizeof(bm), &bm); if (bm.bmWidth > 16 || bm.bmHeight > 16) { HIMAGELIST hImageList; hImageList = ImageList_Create(16, 16, IsWinVerXPPlus() ? ILC_COLOR32 | ILC_MASK : ILC_COLOR16 | ILC_MASK, 1, 0); ImageList_AddIcon(hImageList, (HICON) lParam); lpSBData->hIconPrivate = ImageList_GetIcon(hImageList, 0, ILD_NORMAL); ImageList_RemoveAll(hImageList); ImageList_Destroy(hImageList); lpSBData->hIcon = 0; } else { lpSBData->hIcon = (HICON) lParam; lpSBData->hIconPrivate = NULL; } DeleteObject(ii.hbmMask); DeleteObject(ii.hbmColor); InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); } else if (wParam == IMAGE_BITMAP) { if (lpSBData->hIconPrivate) DestroyIcon(lpSBData->hIconPrivate); lpSBData->hIcon = lpSBData->hIconPrivate = NULL; InvalidateParentRect(lpSBData->hWnd, NULL, TRUE); return 0; // not supported } break; } } return DefWindowProc(hwndDlg, msg, wParam, lParam); }
int TrayCalcChanged(const char *szChangedProto, int averageMode, int netProtoCount) { HICON hIcon; int iIcon; HWND hwnd = pcli->hwndContactList; if (netProtoCount > 1) { if (averageMode > 0) { if (cfg::getByte("CList", "TrayIcon", SETTING_TRAYICON_DEFAULT) == SETTING_TRAYICON_MULTI) { if (cfg::getByte("CList", "AlwaysMulti", SETTING_ALWAYSMULTI_DEFAULT)) { iIcon = IconFromStatusMode(szChangedProto, averageMode, 0, &hIcon); hIcon = (hIcon) ? CopyIcon(hIcon) : ImageList_GetIcon(hCListImages, iIcon, ILD_NORMAL); return pcli->pfnTrayIconSetBaseInfo(hIcon, szChangedProto); } if (pcli->trayIcon == NULL || pcli->trayIcon[0].szProto == NULL) { iIcon = IconFromStatusMode(NULL, averageMode, 0, &hIcon); hIcon = (hIcon) ? CopyIcon(hIcon) : ImageList_GetIcon(hCListImages, iIcon, ILD_NORMAL); return pcli->pfnTrayIconSetBaseInfo(hIcon, NULL); } pcli->pfnTrayIconDestroy(hwnd); pcli->pfnTrayIconInit(hwnd); } else { iIcon = IconFromStatusMode(NULL, averageMode, 0, &hIcon); hIcon = (hIcon) ? CopyIcon(hIcon) : ImageList_GetIcon(hCListImages, iIcon, ILD_NORMAL); return pcli->pfnTrayIconSetBaseInfo(hIcon, NULL); } } else { switch (cfg::getByte("CList", "TrayIcon", SETTING_TRAYICON_DEFAULT)) { case SETTING_TRAYICON_CYCLE: iIcon = IconFromStatusMode(szChangedProto, CallProtoService(szChangedProto, PS_GETSTATUS, 0, 0), 0, &hIcon); pcli->cycleTimerId = SetTimer(NULL, 0, cfg::getWord("CList", "CycleTime", SETTING_CYCLETIME_DEFAULT) * 1000, pcli->pfnTrayCycleTimerProc); hIcon = (hIcon) ? CopyIcon(hIcon) : ImageList_GetIcon(hCListImages, iIcon, ILD_NORMAL); return pcli->pfnTrayIconSetBaseInfo(hIcon, NULL); case SETTING_TRAYICON_MULTI: if (!pcli->trayIcon) pcli->pfnTrayIconRemove(NULL, NULL); else if (cfg::getByte("CList", "AlwaysMulti", SETTING_ALWAYSMULTI_DEFAULT)) { iIcon = IconFromStatusMode(szChangedProto, CallProtoService(szChangedProto, PS_GETSTATUS, 0, 0), 0, &hIcon); hIcon = (hIcon) ? CopyIcon(hIcon) : ImageList_GetIcon(hCListImages, iIcon, ILD_NORMAL); return pcli->pfnTrayIconSetBaseInfo(hIcon, szChangedProto); } pcli->pfnTrayIconDestroy(hwnd); pcli->pfnTrayIconInit(hwnd); break; case SETTING_TRAYICON_SINGLE: ptrA szProto( db_get_sa(NULL, "CList", "PrimaryStatus")); iIcon = IconFromStatusMode(szProto, szProto ? CallProtoService(szProto, PS_GETSTATUS, 0, 0) : CallService(MS_CLIST_GETSTATUSMODE, 0, 0), 0, &hIcon); hIcon = (hIcon) ? CopyIcon(hIcon) : ImageList_GetIcon(hCListImages, iIcon, ILD_NORMAL); return pcli->pfnTrayIconSetBaseInfo(hIcon, NULL); } } } else { iIcon = IconFromStatusMode(NULL, averageMode, 0, &hIcon); hIcon = (hIcon) ? CopyIcon(hIcon) : ImageList_GetIcon(hCListImages, iIcon, ILD_NORMAL); return pcli->pfnTrayIconSetBaseInfo(hIcon, NULL); } return -1; }
static LRESULT CALLBACK TSButtonWndProc(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam) { MButtonCtrl *bct = (MButtonCtrl *) GetWindowLong(hwndDlg, 0); switch (msg) { case WM_NCCREATE: { SetWindowLong(hwndDlg, GWL_STYLE, GetWindowLong(hwndDlg, GWL_STYLE) | BS_OWNERDRAW); bct = malloc(sizeof(MButtonCtrl)); if (bct == NULL) return FALSE; bct->hwnd = hwndDlg; bct->stateId = PBS_NORMAL; bct->focus = 0; bct->hFont = GetStockObject(DEFAULT_GUI_FONT); bct->arrow = NULL; bct->defbutton = 0; bct->hIcon = bct->hIconPrivate = 0; bct->iIcon = 0; bct->hIml = 0; bct->hBitmap = NULL; bct->pushBtn = 0; bct->pbState = 0; bct->hThemeButton = NULL; bct->hThemeToolbar = NULL; bct->cHot = 0; bct->flatBtn = 0; bct->bThemed = FALSE; bct->bSkinned = bct->bSendOnDown = 0; bct->buttonItem = NULL; LoadTheme(bct); SetWindowLong(hwndDlg, 0, (LONG) bct); if (((CREATESTRUCTA *) lParam)->lpszName) SetWindowText(hwndDlg, ((CREATESTRUCT *) lParam)->lpszName); return TRUE; } case WM_DESTROY: { if (bct) { if (hwndToolTips) { TOOLINFO ti; ZeroMemory(&ti, sizeof(ti)); ti.cbSize = sizeof(ti); ti.uFlags = TTF_IDISHWND; ti.hwnd = bct->hwnd; ti.uId = (UINT) bct->hwnd; if (SendMessage(hwndToolTips, TTM_GETTOOLINFO, 0, (LPARAM) &ti)) { SendMessage(hwndToolTips, TTM_DELTOOL, 0, (LPARAM) &ti); } if (SendMessage(hwndToolTips, TTM_GETTOOLCOUNT, 0, (LPARAM) &ti) == 0) { DestroyWindow(hwndToolTips); hwndToolTips = NULL; } } if (bct->hIconPrivate) DestroyIcon(bct->hIconPrivate); DestroyTheme(bct); free(bct); } SetWindowLong(hwndDlg, 0, (LONG) NULL); break; // DONT! fall thru } case WM_SETTEXT: { bct->cHot = 0; if ((char*) lParam) { char *tmp = (char *) lParam; while (*tmp) { if (*tmp == '&' && *(tmp + 1)) { bct->cHot = tolower(*(tmp + 1)); break; } tmp++; } InvalidateRect(bct->hwnd, NULL, TRUE); lstrcpyn(bct->szText, (TCHAR *)lParam, 127); bct->szText[127] = 0; } break; } case WM_SYSKEYUP: if (bct->stateId != PBS_DISABLED && bct->cHot && bct->cHot == tolower((int) wParam)) { if (bct->pushBtn) { if (bct->pbState) bct->pbState = 0; else bct->pbState = 1; InvalidateRect(bct->hwnd, NULL, TRUE); } if(!bct->bSendOnDown) SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(GetDlgCtrlID(hwndDlg), BN_CLICKED), (LPARAM) hwndDlg); return 0; } break; case WM_THEMECHANGED: { // themed changed, reload theme object if (bct->bThemed) LoadTheme(bct); InvalidateRect(bct->hwnd, NULL, TRUE); // repaint it break; } case WM_SETFONT: // remember the font so we can use it later { bct->hFont = (HFONT) wParam; // maybe we should redraw? break; } case WM_NCPAINT: case WM_PAINT: { PAINTSTRUCT ps; HDC hdcPaint; hdcPaint = BeginPaint(hwndDlg, &ps); if (hdcPaint) { PaintWorker(bct, hdcPaint); EndPaint(hwndDlg, &ps); } break; } case BM_GETIMAGE: if(wParam == IMAGE_ICON) return (LRESULT)(bct->hIconPrivate ? bct->hIconPrivate : bct->hIcon); break; case BM_SETIMAGE: if(!lParam) break; bct->hIml = 0; bct->iIcon = 0; if (wParam == IMAGE_ICON) { ICONINFO ii = {0}; BITMAP bm = {0}; if (bct->hIconPrivate) { DestroyIcon(bct->hIconPrivate); bct->hIconPrivate = 0; } GetIconInfo((HICON) lParam, &ii); GetObject(ii.hbmColor, sizeof(bm), &bm); if (bm.bmWidth > g_cxsmIcon || bm.bmHeight > g_cysmIcon) { HIMAGELIST hImageList; hImageList = ImageList_Create(g_cxsmIcon, g_cysmIcon, IsWinVerXPPlus() ? ILC_COLOR32 | ILC_MASK : ILC_COLOR16 | ILC_MASK, 1, 0); ImageList_AddIcon(hImageList, (HICON) lParam); bct->hIconPrivate = ImageList_GetIcon(hImageList, 0, ILD_NORMAL); ImageList_RemoveAll(hImageList); ImageList_Destroy(hImageList); bct->hIcon = 0; } else { bct->hIcon = (HICON) lParam; bct->hIconPrivate = 0; } DeleteObject(ii.hbmMask); DeleteObject(ii.hbmColor); bct->hBitmap = NULL; InvalidateRect(bct->hwnd, NULL, TRUE); } else if (wParam == IMAGE_BITMAP) { bct->hBitmap = (HBITMAP) lParam; if (bct->hIconPrivate) DestroyIcon(bct->hIconPrivate); bct->hIcon = bct->hIconPrivate = NULL; InvalidateRect(bct->hwnd, NULL, TRUE); } break; case BM_SETPRIVATEICON: bct->hIml = 0; bct->iIcon = 0; { if (bct->hIconPrivate) DestroyIcon(bct->hIconPrivate); bct->hIconPrivate = DuplicateIcon(g_hInst, (HICON) lParam); bct->hIcon = 0; break; } case BM_SETIMLICON: { if (bct->hIconPrivate) DestroyIcon(bct->hIconPrivate); bct->hIml = (HIMAGELIST) wParam; bct->iIcon = (int) lParam; bct->hIcon = bct->hIconPrivate = 0; InvalidateRect(bct->hwnd, NULL, TRUE); break; } case BM_SETSKINNED: bct->bSkinned = (DWORD)lParam; bct->bThemed = bct->bSkinned ? FALSE : bct->bThemed; InvalidateRect(bct->hwnd, NULL, TRUE); break; case BM_SETBTNITEM: bct->buttonItem = (ButtonItem *)lParam; break; case BM_SETASMENUACTION: bct->bSendOnDown = wParam ? TRUE : FALSE; return 0; case BM_SETCHECK: if (!bct->pushBtn) break; if (wParam == BST_CHECKED) { bct->pbState = 1; bct->stateId = PBS_PRESSED; } else if (wParam == BST_UNCHECKED) { bct->pbState = 0; bct->stateId = PBS_NORMAL; } InvalidateRect(bct->hwnd, NULL, TRUE); break; case BM_GETCHECK: if (bct->pushBtn) { return bct->pbState ? BST_CHECKED : BST_UNCHECKED; } return 0; case BUTTONSETARROW: // turn arrow on/off if (wParam) { if (!bct->arrow) bct->arrow = (HICON) LoadImage(g_hInst, MAKEINTRESOURCE(IDI_MINIMIZE), IMAGE_ICON, g_cxsmIcon, g_cysmIcon, 0); } else { if (bct->arrow) { DestroyIcon(bct->arrow); bct->arrow = NULL; } } InvalidateRect(bct->hwnd, NULL, TRUE); break; case BUTTONSETDEFAULT: bct->defbutton = wParam ? 1 : 0; InvalidateRect(bct->hwnd, NULL, TRUE); break; case BUTTONSETASPUSHBTN: bct->pushBtn = 1; InvalidateRect(bct->hwnd, NULL, TRUE); break; case BUTTONSETASFLATBTN: bct->flatBtn = lParam == 0 ? 1 : 0; InvalidateRect(bct->hwnd, NULL, TRUE); break; case BUTTONSETASFLATBTN + 10: bct->bThemed = lParam ? TRUE : FALSE; bct->bSkinned = bct->bThemed ? 0 : bct->bSkinned; break; case BUTTONADDTOOLTIP: { TOOLINFO ti; if (!(char*) wParam) break; if (!hwndToolTips) { hwndToolTips = CreateWindowEx(WS_EX_TOPMOST, TOOLTIPS_CLASS, _T(""), WS_POPUP, 0, 0, 0, 0, NULL, NULL, GetModuleHandle(NULL), NULL); SetWindowPos(hwndToolTips, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOSIZE | SWP_NOMOVE); } ZeroMemory(&ti, sizeof(ti)); ti.cbSize = sizeof(ti); ti.uFlags = TTF_IDISHWND; ti.hwnd = bct->hwnd; ti.uId = (UINT) bct->hwnd; if (SendMessage(hwndToolTips, TTM_GETTOOLINFO, 0, (LPARAM) &ti)) { SendMessage(hwndToolTips, TTM_DELTOOL, 0, (LPARAM) &ti); } ti.uFlags = TTF_IDISHWND | TTF_SUBCLASS; ti.uId = (UINT) bct->hwnd; ti.lpszText = (TCHAR *) wParam; SendMessage(hwndToolTips, TTM_ADDTOOL, 0, (LPARAM) &ti); break; } case WM_SETFOCUS: // set keybord focus and redraw bct->focus = 1; InvalidateRect(bct->hwnd, NULL, TRUE); break; case WM_KILLFOCUS: // kill focus and redraw bct->focus = 0; InvalidateRect(bct->hwnd, NULL, TRUE); break; case WM_WINDOWPOSCHANGED: InvalidateRect(bct->hwnd, NULL, TRUE); break; case WM_ENABLE: // windows tells us to enable/disable { bct->stateId = wParam ? PBS_NORMAL : PBS_DISABLED; InvalidateRect(bct->hwnd, NULL, TRUE); break; } case WM_MOUSELEAVE: // faked by the WM_TIMER { if (bct->stateId != PBS_DISABLED) { // don't change states if disabled bct->stateId = PBS_NORMAL; InvalidateRect(bct->hwnd, NULL, TRUE); } break; } case WM_LBUTTONDOWN: { if (bct->stateId != PBS_DISABLED && bct->stateId != PBS_PRESSED) { bct->stateId = PBS_PRESSED; InvalidateRect(bct->hwnd, NULL, TRUE); if(bct->bSendOnDown) { SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(GetDlgCtrlID(hwndDlg), BN_CLICKED), (LPARAM) hwndDlg); bct->stateId = PBS_NORMAL; InvalidateRect(bct->hwnd, NULL, TRUE); } } break; } case WM_LBUTTONUP: { if (bct->pushBtn) { if (bct->pbState) bct->pbState = 0; else bct->pbState = 1; } if (bct->stateId != PBS_DISABLED) { // don't change states if disabled if (msg == WM_LBUTTONUP) bct->stateId = PBS_HOT; else bct->stateId = PBS_NORMAL; InvalidateRect(bct->hwnd, NULL, TRUE); } if(!bct->bSendOnDown) SendMessage(GetParent(hwndDlg), WM_COMMAND, MAKELONG(GetDlgCtrlID(hwndDlg), BN_CLICKED), (LPARAM) hwndDlg); break; } case WM_MOUSEMOVE: if (bct->stateId == PBS_NORMAL) { bct->stateId = PBS_HOT; InvalidateRect(bct->hwnd, NULL, TRUE); } // Call timer, used to start cheesy TrackMouseEvent faker SetTimer(hwndDlg, BUTTON_POLLID, BUTTON_POLLDELAY, NULL); break; case WM_NCHITTEST: { LRESULT lr = SendMessage(GetParent(hwndDlg), WM_NCHITTEST, wParam, lParam); if(lr == HTLEFT || lr == HTRIGHT || lr == HTBOTTOM || lr == HTTOP || lr == HTTOPLEFT || lr == HTTOPRIGHT || lr == HTBOTTOMLEFT || lr == HTBOTTOMRIGHT) return HTTRANSPARENT; break; } case WM_TIMER: // use a timer to check if they have did a mouseout { if (wParam == BUTTON_POLLID) { RECT rc; POINT pt; GetWindowRect(hwndDlg, &rc); GetCursorPos(&pt); if (!PtInRect(&rc, pt)) { // mouse must be gone, trigger mouse leave PostMessage(hwndDlg, WM_MOUSELEAVE, 0, 0L); KillTimer(hwndDlg, BUTTON_POLLID); } } break; } case WM_ERASEBKGND: return 1; } return DefWindowProc(hwndDlg, msg, wParam, lParam); }
void ThumbInfo::UpdateContent() { bmpContent.allocate(szSize.cx, szSize.cy); HFONT hOldFont; SIZE size; RECT rc, rcText; DWORD oldColor; int oldBkMode, index = 0;// nStatus; UINT fStyle = ILD_NORMAL; HDC hdcDraw = bmpContent.getDC(); SetRect(&rc, 0, 0, szSize.cx, szSize.cy); if (nullptr != hBmpBackground) { RECT rcBkgnd; SetRect(&rcBkgnd, 0, 0, szSize.cx, szSize.cy); if (nullptr != hLTEdgesPen) InflateRect(&rcBkgnd, -1, -1); int width = rcBkgnd.right - rcBkgnd.left; int height = rcBkgnd.bottom - rcBkgnd.top; BITMAP bmp; GetObject(hBmpBackground, sizeof(bmp), &bmp); HDC hdcBmp = CreateCompatibleDC(hdcDraw); HBITMAP hbmTmp = (HBITMAP)SelectObject(hdcBmp, hBmpBackground); int maxx = (0 != (nBackgroundBmpUse & CLBF_TILEH) ? rcBkgnd.right : rcBkgnd.left + 1); int maxy = (0 != (nBackgroundBmpUse & CLBF_TILEV) ? rcBkgnd.bottom : rcBkgnd.top + 1); int destw, desth; switch (nBackgroundBmpUse & CLBM_TYPE) { case CLB_STRETCH: if (0 != (nBackgroundBmpUse & CLBF_PROPORTIONAL)) { if (width * bmp.bmHeight < height * bmp.bmWidth) { desth = height; destw = desth * bmp.bmWidth / bmp.bmHeight; } else { destw = width; desth = destw * bmp.bmHeight / bmp.bmWidth; } } else { destw = width; desth = height; } break; case CLB_STRETCHH: destw = width; if (0 != (nBackgroundBmpUse & CLBF_PROPORTIONAL)) desth = destw * bmp.bmHeight / bmp.bmWidth; else desth = bmp.bmHeight; break; case CLB_STRETCHV: desth = height; if (0 != (nBackgroundBmpUse & CLBF_PROPORTIONAL)) destw = desth * bmp.bmWidth / bmp.bmHeight; else destw = bmp.bmWidth; break; default: //clb_topleft destw = bmp.bmWidth; desth = bmp.bmHeight; break; } SetStretchBltMode(hdcBmp, STRETCH_HALFTONE); for (int x = rcBkgnd.left; x < maxx; x += destw) for (int y = rcBkgnd.top; y < maxy; y += desth) StretchBlt(hdcDraw, x, y, destw, desth, hdcBmp, 0, 0, bmp.bmWidth, bmp.bmHeight, SRCCOPY); SelectObject(hdcBmp, hbmTmp); DeleteDC(hdcBmp); } else FillRect(hdcDraw, &rc, hBkBrush); if (nullptr != hLTEdgesPen) { HPEN hOldPen = (HPEN)SelectObject(hdcDraw, hLTEdgesPen); MoveToEx(hdcDraw, 0, 0, nullptr); LineTo(hdcDraw, szSize.cx, 0); MoveToEx(hdcDraw, 0, 0, nullptr); LineTo(hdcDraw, 0, szSize.cy); SelectObject(hdcDraw, hRBEdgesPen); MoveToEx(hdcDraw, 0, szSize.cy - 1, nullptr); LineTo(hdcDraw, szSize.cx - 1, szSize.cy - 1); MoveToEx(hdcDraw, szSize.cx - 1, szSize.cy - 1, nullptr); LineTo(hdcDraw, szSize.cx - 1, 0); SelectObject(hdcDraw, hOldPen); } bmpContent.setAlpha(btAlpha); ImageList_GetIconSize_my(himlMiranda, size); oldBkMode = SetBkMode(hdcDraw, TRANSPARENT); if (!db_get_b(hContact, "CList", "NotOnList", 0)) { char *szProto = GetContactProto(hContact); if (nullptr != szProto) { int nStatus = Proto_GetStatus(szProto); int nContactStatus = db_get_w(hContact, szProto, "Status", ID_STATUS_OFFLINE); int nApparentMode = db_get_w(hContact, szProto, "ApparentMode", 0); if ((nStatus == ID_STATUS_INVISIBLE && nApparentMode == ID_STATUS_ONLINE) || (nStatus != ID_STATUS_INVISIBLE && nApparentMode == ID_STATUS_OFFLINE)) { if (ID_STATUS_OFFLINE == nContactStatus) index = FLT_FONTID_OFFINVIS; else { index = FLT_FONTID_INVIS; if (fcOpt.bShowIdle && db_get_dw(hContact, szProto, "IdleTS", 0)) fStyle |= ILD_BLEND50; } } else if (ID_STATUS_OFFLINE == nContactStatus) { index = FLT_FONTID_OFFLINE; } else { index = FLT_FONTID_CONTACTS; if (fcOpt.bShowIdle && db_get_dw(hContact, szProto, "IdleTS", 0)) fStyle |= ILD_BLEND50; } } } else { index = FLT_FONTID_NOTONLIST; fStyle |= ILD_BLEND50; } oldColor = SetTextColor(hdcDraw, tColor[index]); HICON icon = ImageList_GetIcon(himlMiranda, iIcon, ILD_NORMAL); MyBitmap bmptmp(size.cx, size.cy); bmptmp.DrawIcon(icon, 0, 0);//bmpContent BLENDFUNCTION blend; blend.BlendOp = AC_SRC_OVER; blend.BlendFlags = 0; blend.SourceConstantAlpha = (fStyle&ILD_BLEND50) ? 128 : 255; blend.AlphaFormat = AC_SRC_ALPHA; AlphaBlend(hdcDraw, 2, (szSize.cy - size.cx) / 2, bmptmp.getWidth(), bmptmp.getHeight(), bmptmp.getDC(), 0, 0, bmptmp.getWidth(), bmptmp.getHeight(), blend); DestroyIcon(icon); SetRect(&rcText, 0, 0, szSize.cx, szSize.cy); rcText.left += size.cx + 4; hOldFont = (HFONT)SelectObject(hdcDraw, hFont[index]); SIZE szText; GetTextExtentPoint32(hdcDraw, ptszName, (int)mir_wstrlen(ptszName), &szText); SetTextColor(hdcDraw, bkColor); // simple border bmpContent.DrawText(ptszName, rcText.left - 1, (rcText.top + rcText.bottom - szText.cy) / 2); bmpContent.DrawText(ptszName, rcText.left + 1, (rcText.top + rcText.bottom - szText.cy) / 2); bmpContent.DrawText(ptszName, rcText.left, (rcText.top + rcText.bottom - szText.cy) / 2 - 1); bmpContent.DrawText(ptszName, rcText.left, (rcText.top + rcText.bottom - szText.cy) / 2 + 1); // blurred border // bmpContent.DrawText(ptszName, rcText.left, (rcText.top + rcText.bottom - szText.cy)/2, 3); // text itself SetTextColor(hdcDraw, tColor[index]); bmpContent.DrawText(ptszName, rcText.left, (rcText.top + rcText.bottom - szText.cy) / 2); SelectObject(hdcDraw, hOldFont); SetTextColor(hdcDraw, oldColor); SetBkMode(hdcDraw, oldBkMode); SetWindowLongPtr(hwnd, GWL_EXSTYLE, GetWindowLongPtr(hwnd, GWL_EXSTYLE) | WS_EX_LAYERED); GetWindowRect(hwnd, &rc); POINT ptDst = { rc.left, rc.top }; POINT ptSrc = { 0, 0 }; blend.BlendOp = AC_SRC_OVER; blend.BlendFlags = 0; blend.SourceConstantAlpha = 255; blend.AlphaFormat = AC_SRC_ALPHA; UpdateLayeredWindow(hwnd, nullptr, &ptDst, &szSize, bmpContent.getDC(), &ptSrc, 0xffffffff, &blend, ULW_ALPHA); }
static INT_PTR CALLBACK DlgProcVisibilityOpts(HWND hwndDlg, UINT msg, WPARAM, LPARAM lParam) { static HICON hVisibleIcon, hInvisibleIcon; static HANDLE hItemAll; HIMAGELIST hIml; switch (msg) { case WM_INITDIALOG: TranslateDialogDefault(hwndDlg); hIml = ImageList_Create(GetSystemMetrics(SM_CXSMICON), GetSystemMetrics(SM_CYSMICON), ILC_COLOR32 | ILC_MASK, 3, 3); ImageList_AddIcon_IconLibLoaded(hIml, SKINICON_OTHER_SMALLDOT); ImageList_AddIcon_IconLibLoaded(hIml, SKINICON_OTHER_VISIBLE_ALL); ImageList_AddIcon_IconLibLoaded(hIml, SKINICON_OTHER_INVISIBLE_ALL); SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_SETEXTRAIMAGELIST, 0, (LPARAM)hIml); hVisibleIcon = ImageList_GetIcon(hIml, 1, ILD_NORMAL); SendDlgItemMessage(hwndDlg, IDC_VISIBLEICON, STM_SETICON, (WPARAM)hVisibleIcon, 0); hInvisibleIcon = ImageList_GetIcon(hIml, 2, ILD_NORMAL); SendDlgItemMessage(hwndDlg, IDC_INVISIBLEICON, STM_SETICON, (WPARAM)hInvisibleIcon, 0); ResetListOptions( GetDlgItem(hwndDlg, IDC_LIST)); SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_SETEXTRACOLUMNS, 2, 0); { CLCINFOITEM cii = { sizeof(cii) }; cii.flags = CLCIIF_GROUPFONT; cii.pszText = TranslateT("** All contacts **"); hItemAll = (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_ADDINFOITEM, 0, (LPARAM)&cii); } SetAllContactIcons( GetDlgItem(hwndDlg, IDC_LIST)); SetListGroupIcons( GetDlgItem(hwndDlg, IDC_LIST), (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETNEXTITEM, CLGN_ROOT, 0), hItemAll, NULL); return TRUE; case WM_SETFOCUS: SetFocus( GetDlgItem(hwndDlg, IDC_LIST)); break; case WM_NOTIFY: switch(((LPNMHDR)lParam)->idFrom) { case IDC_LIST: switch (((LPNMHDR)lParam)->code) { case CLN_NEWCONTACT: case CLN_LISTREBUILT: SetAllContactIcons( GetDlgItem(hwndDlg, IDC_LIST)); //fall through case CLN_CONTACTMOVED: SetListGroupIcons( GetDlgItem(hwndDlg, IDC_LIST), (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETNEXTITEM, CLGN_ROOT, 0), hItemAll, NULL); break; case CLN_OPTIONSCHANGED: ResetListOptions( GetDlgItem(hwndDlg, IDC_LIST)); break; case NM_CLICK: { // Make sure we have an extra column NMCLISTCONTROL *nm = (NMCLISTCONTROL*)lParam; if (nm->iColumn == -1) break; // Find clicked item DWORD hitFlags; HANDLE hItem = (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_HITTEST, (WPARAM)&hitFlags, MAKELPARAM(nm->pt.x, nm->pt.y)); if (hItem == NULL) break; // It was not a visbility icon if (!(hitFlags & CLCHT_ONITEMEXTRA)) break; // Get image in clicked column (0 = none, 1 = visible, 2 = invisible) int iImage = SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETEXTRAIMAGE, (WPARAM)hItem, MAKELPARAM(nm->iColumn, 0)); if (iImage == 0) iImage = nm->iColumn + 1; else if (iImage == 1 || iImage == 2) iImage = 0; // Get item type (contact, group, etc...) int itemType = SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETITEMTYPE, (WPARAM)hItem, 0); // Update list, making sure that the options are mutually exclusive if (itemType == CLCIT_CONTACT) { // A contact SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_SETEXTRAIMAGE, (WPARAM)hItem, MAKELPARAM(nm->iColumn, iImage)); if (iImage && SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETEXTRAIMAGE, (WPARAM)hItem, MAKELPARAM(nm->iColumn?0:1, 0)) != EMPTY_EXTRA_ICON) SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_SETEXTRAIMAGE, (WPARAM)hItem, MAKELPARAM(nm->iColumn?0:1, 0)); } else if (itemType == CLCIT_INFO) { // All Contacts SetAllChildIcons( GetDlgItem(hwndDlg, IDC_LIST), hItem, nm->iColumn, iImage); if (iImage) SetAllChildIcons( GetDlgItem(hwndDlg, IDC_LIST), hItem, nm->iColumn?0:1, 0); } else if (itemType == CLCIT_GROUP) { // A group hItem = (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETNEXTITEM, CLGN_CHILD, (LPARAM)hItem); if (hItem) { SetAllChildIcons( GetDlgItem(hwndDlg, IDC_LIST), hItem, nm->iColumn, iImage); if (iImage) SetAllChildIcons( GetDlgItem(hwndDlg, IDC_LIST), hItem, nm->iColumn?0:1, 0); } } // Update the all/none icons SetListGroupIcons( GetDlgItem(hwndDlg, IDC_LIST), (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETNEXTITEM, CLGN_ROOT, 0), hItemAll, NULL); // Activate Apply button SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0); } } break; case 0: if (((LPNMHDR)lParam)->code == PSN_APPLY) { for (MCONTACT hContact = db_find_first(); hContact; hContact = db_find_next(hContact)) { HANDLE hItem = (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_FINDCONTACT, hContact, 0); if (hItem == NULL) continue; int set = 0; for (int i=0; i < 2; i++) { int iImage = SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETEXTRAIMAGE, (WPARAM)hItem, MAKELPARAM(i, 0)); if (iImage == i+1) { CallContactService(hContact, PSS_SETAPPARENTMODE, iImage == 1?ID_STATUS_ONLINE:ID_STATUS_OFFLINE, 0); set = 1; break; } } if (!set) CallContactService(hContact, PSS_SETAPPARENTMODE, 0, 0); } return TRUE; } } break; case WM_DESTROY: DestroyIcon(hVisibleIcon); DestroyIcon(hInvisibleIcon); hIml = (HIMAGELIST)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETEXTRAIMAGELIST, 0, 0); ImageList_Destroy(hIml); break; } return FALSE; }
INT_PTR CALLBACK DlgProcIgnoreOptions(HWND hwndDlg, UINT msg, WPARAM, LPARAM lParam) { static HICON hIcons[IGNOREEVENT_MAX+2]; static HANDLE hItemAll, hItemUnknown; switch (msg) { case WM_INITDIALOG: TranslateDialogDefault(hwndDlg); { HIMAGELIST hIml=ImageList_Create(GetSystemMetrics(SM_CXSMICON), GetSystemMetrics(SM_CYSMICON), ILC_COLOR32 | ILC_MASK, 3+IGNOREEVENT_MAX, 3+IGNOREEVENT_MAX); ImageList_AddIcon(hIml, Skin_LoadIcon(SKINICON_OTHER_SMALLDOT)); ImageList_AddIcon(hIml, Skin_LoadIcon(SKINICON_OTHER_FILLEDBLOB)); ImageList_AddIcon(hIml, Skin_LoadIcon(SKINICON_OTHER_EMPTYBLOB)); ImageList_AddIcon(hIml, Skin_LoadIcon(SKINICON_EVENT_MESSAGE)); ImageList_AddIcon(hIml, Skin_LoadIcon(SKINICON_EVENT_URL)); ImageList_AddIcon(hIml, Skin_LoadIcon(SKINICON_EVENT_FILE)); ImageList_AddIcon(hIml, Skin_LoadIcon(SKINICON_OTHER_MIRANDA)); SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_SETEXTRAIMAGELIST, 0, (LPARAM)hIml); for (int i=0; i < _countof(hIcons); i++) hIcons[i] = ImageList_GetIcon(hIml, 1+i, ILD_NORMAL); } SendDlgItemMessage(hwndDlg, IDC_ALLICON, STM_SETICON, (WPARAM)hIcons[0], 0); SendDlgItemMessage(hwndDlg, IDC_NONEICON, STM_SETICON, (WPARAM)hIcons[1], 0); SendDlgItemMessage(hwndDlg, IDC_MSGICON, STM_SETICON, (WPARAM)hIcons[2], 0); SendDlgItemMessage(hwndDlg, IDC_URLICON, STM_SETICON, (WPARAM)hIcons[3], 0); SendDlgItemMessage(hwndDlg, IDC_FILEICON, STM_SETICON, (WPARAM)hIcons[4], 0); SendDlgItemMessage(hwndDlg, IDC_OTHERICON, STM_SETICON, (WPARAM)hIcons[5], 0); SetWindowLongPtr(GetDlgItem(hwndDlg, IDC_LIST), GWL_STYLE, GetWindowLongPtr(GetDlgItem(hwndDlg, IDC_LIST), GWL_STYLE) &~ (CLS_CHECKBOXES|CLS_GROUPCHECKBOXES)); SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_AUTOREBUILD, 0, 0); ResetListOptions(GetDlgItem(hwndDlg, IDC_LIST)); SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_SETEXTRACOLUMNS, IGNOREEVENT_MAX+2, 0); { CLCINFOITEM cii = {0}; cii.cbSize = sizeof(cii); cii.flags = CLCIIF_GROUPFONT; cii.pszText = TranslateT("** All contacts **"); hItemAll=(HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_ADDINFOITEM, 0, (LPARAM)&cii); cii.pszText = TranslateT("** Unknown contacts **"); hItemUnknown=(HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST,CLM_ADDINFOITEM, 0, (LPARAM)&cii); InitialiseItem(GetDlgItem(hwndDlg, IDC_LIST), NULL, hItemUnknown, 0xFFFFFFFF); } SetAllContactIcons(GetDlgItem(hwndDlg, IDC_LIST)); SetListGroupIcons(GetDlgItem(hwndDlg, IDC_LIST),(HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETNEXTITEM, CLGN_ROOT, 0), hItemAll, NULL); return TRUE; case WM_SETFOCUS: SetFocus(GetDlgItem(hwndDlg, IDC_LIST)); break; case WM_NOTIFY: switch(((LPNMHDR)lParam)->idFrom) { case IDC_LIST: switch (((LPNMHDR)lParam)->code) { case CLN_NEWCONTACT: case CLN_LISTREBUILT: SetAllContactIcons(GetDlgItem(hwndDlg, IDC_LIST)); //fall through case CLN_CONTACTMOVED: SetListGroupIcons(GetDlgItem(hwndDlg, IDC_LIST), (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETNEXTITEM, CLGN_ROOT, 0), hItemAll, NULL); break; case CLN_OPTIONSCHANGED: ResetListOptions(GetDlgItem(hwndDlg, IDC_LIST)); break; case CLN_CHECKCHANGED: SendMessage(GetParent(GetParent(hwndDlg)), PSM_CHANGED, 0, 0); break; case NM_CLICK: { int iImage; HANDLE hItem; DWORD hitFlags; NMCLISTCONTROL *nm = (NMCLISTCONTROL*)lParam; if(nm->iColumn == -1) break; hItem = (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_HITTEST, (WPARAM)&hitFlags, MAKELPARAM(nm->pt.x, nm->pt.y)); if(hItem == NULL) break; if (!(hitFlags & CLCHT_ONITEMEXTRA)) break; if(nm->iColumn == IGNOREEVENT_MAX) { //ignore all for (iImage=0; iImage < IGNOREEVENT_MAX; iImage++) SetIconsForColumn(GetDlgItem(hwndDlg, IDC_LIST), hItem, hItemAll, iImage, iImage+3); } else if(nm->iColumn == IGNOREEVENT_MAX+1) { //ignore none for (iImage=0; iImage < IGNOREEVENT_MAX; iImage++) SetIconsForColumn(GetDlgItem(hwndDlg, IDC_LIST), hItem, hItemAll, iImage, 0); } else { iImage = SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETEXTRAIMAGE, (WPARAM)hItem, MAKELPARAM(nm->iColumn, 0)); if(iImage == 0) iImage = nm->iColumn + 3; else if(iImage != EMPTY_EXTRA_ICON) iImage = 0; SetIconsForColumn(GetDlgItem(hwndDlg, IDC_LIST), hItem, hItemAll, nm->iColumn, iImage); } SetListGroupIcons(GetDlgItem(hwndDlg, IDC_LIST),(HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETNEXTITEM, CLGN_ROOT, 0), hItemAll, NULL); SendMessage(GetParent(GetParent(hwndDlg)), PSM_CHANGED, 0, 0); break; } } break; case 0: switch (((LPNMHDR)lParam)->code) { case PSN_APPLY: { for (MCONTACT hContact = db_find_first(); hContact; hContact = db_find_next(hContact)) { HANDLE hItem = (HANDLE)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_FINDCONTACT, hContact, 0); if(hItem) SaveItemMask(GetDlgItem(hwndDlg, IDC_LIST), hContact, hItem, "Mask1"); } SaveItemMask(GetDlgItem(hwndDlg, IDC_LIST), NULL, hItemAll, "Default1"); SaveItemMask(GetDlgItem(hwndDlg, IDC_LIST), NULL, hItemUnknown, "Mask1"); return TRUE; } } break; } break; case WM_DESTROY: { int i; HIMAGELIST hIml; for (i=0; i < _countof(hIcons); i++) DestroyIcon(hIcons[i]); hIml = (HIMAGELIST)SendDlgItemMessage(hwndDlg, IDC_LIST, CLM_GETEXTRAIMAGELIST, 0, 0); ImageList_Destroy(hIml); break; } } return FALSE; }
/** Called when the context-menu of a contact is about to be displayed * * This will test which of the 4 menu item should be displayed, depending * on which contact triggered the event * * @param wParam : \c HANDLE to the contact that triggered the event * @param lParam : Always set to 0; */ int Meta_ModifyMenu(WPARAM wParam, LPARAM lParam) { CLISTMENUITEM mi; DBVARIANT dbv; HANDLE hContact; char *proto; char buf[512], buffer2[512]; int i, iconIndex; WORD status; mi.flags = CMIM_FLAGS; mi.cbSize = sizeof(CLISTMENUITEM); if(DBGetContactSettingDword((HANDLE)wParam,META_PROTO,META_ID,-1) != (DWORD)-1) { int num_contacts, i; // save the mouse pos in case they open a subcontact menu GetCursorPos(&menuMousePoint); // This is a MetaContact, show the edit, force default, and the delete menu, and hide the others CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuEdit, (LPARAM)&mi); //mi.flags |= CMIM_NAME; //if(DBGetContactSettingByte((HANDLE)wParam, META_PROTO, "ForceDefault", 0)) // mi.pszName = Translate("Unforce Default"); //else // mi.pszName = Translate("Force Default"); //CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuForceDefault, (LPARAM)&mi); mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuAdd, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuConvert, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDefault, (LPARAM)&mi); mi.flags = CMIM_FLAGS | CMIM_NAME | CMIF_HIDDEN; // we don't need delete - already in contact menu mi.pszName = Translate("Delete MetaContact"); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDelete, (LPARAM)&mi); //show subcontact menu items num_contacts = DBGetContactSettingDword((HANDLE)wParam, META_PROTO, "NumContacts", 0); for(i = 0; i < MAX_CONTACTS; i++) { if(i < num_contacts) { hContact = Meta_GetContactHandle((HANDLE)wParam, i); proto = _strdup((char *)CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)hContact, 0)); if(!proto) status = ID_STATUS_OFFLINE; else status = DBGetContactSettingWord(hContact, proto, "Status", ID_STATUS_OFFLINE); if(options.menu_contact_label == DNT_UID) { strcpy(buf, "Login"); strcat(buf, _itoa(i, buffer2, 10)); DBGetContactSetting((HANDLE)wParam,META_PROTO,buf,&dbv); switch(dbv.type) { case DBVT_ASCIIZ: mir_snprintf(buf,512,"%s",dbv.pszVal); break; case DBVT_BYTE: mir_snprintf(buf,512,"%d",dbv.bVal); break; case DBVT_WORD: mir_snprintf(buf,512,"%d",dbv.wVal); break; case DBVT_DWORD: mir_snprintf(buf,512,"%d",dbv.dVal); break; default: buf[0] = 0; } DBFreeVariant(&dbv); mi.pszName = buf; mi.flags = 0; } else { char *name = (char *)CallService(MS_CLIST_GETCONTACTDISPLAYNAME, (WPARAM)hContact, 0); char *wname = (char *)CallService(MS_CLIST_GETCONTACTDISPLAYNAME, (WPARAM)hContact, GCDNF_UNICODE); if(wname && strncmp(name, wname, strlen(name)) != 0) { mi.pszName = wname; mi.flags = CMIF_UNICODE; } else { mi.pszName = name; mi.flags = 0; } } mi.flags |= CMIM_FLAGS | CMIM_NAME | CMIM_ICON; //mi.hIcon = LoadSkinnedProtoIcon(proto, status); iconIndex = (int)CallService(MS_CLIST_GETCONTACTICON, (WPARAM)hContact, 0); mi.hIcon = ImageList_GetIcon((HIMAGELIST)CallService(MS_CLIST_GETICONSIMAGELIST, 0, 0), iconIndex, 0);; free(proto); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuContact[i], (LPARAM)&mi); DestroyIcon(mi.hIcon); //CallService(MS_SKIN2_RELEASEICON, (WPARAM)mi.hIcon, 0); } else { mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuContact[i], (LPARAM)&mi); } } // show hide nudge menu item #define MS_NUDGE_SHOWMENU "NudgeShowMenu" // wParam = char *szProto // lParam = BOOL show { char serviceFunc[256]; hContact = Meta_GetMostOnline((HANDLE)wParam); mir_snprintf(serviceFunc, 256, "%s/SendNudge", (char *)CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)hContact, 0)); CallService(MS_NUDGE_SHOWMENU, (WPARAM)META_PROTO, (LPARAM)ServiceExists(serviceFunc)); } } else {// This is a simple contact if(!Meta_IsEnabled()) { // groups disabled - all meta menu options hidden mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDefault, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDelete, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuAdd, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuConvert, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuEdit, (LPARAM)&mi); for(i = 0; i < MAX_CONTACTS; i++) { mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuContact[i], (LPARAM)&mi); } } else if(DBGetContactSettingDword((HANDLE)wParam,META_PROTO,META_LINK,(DWORD)-1)!=(DWORD)-1) { // The contact is affected to a metacontact. CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDefault, (LPARAM)&mi); mi.flags |= CMIM_NAME; mi.pszName = (char *)Translate("Remove from MetaContact"); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDelete, (LPARAM)&mi); mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuAdd, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuConvert, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuEdit, (LPARAM)&mi); for(i = 0; i < MAX_CONTACTS; i++) { mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuContact[i], (LPARAM)&mi); } } else { // The contact is neutral CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuAdd, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuConvert, (LPARAM)&mi); mi.flags |= CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuEdit, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDelete, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDefault, (LPARAM)&mi); for(i = 0; i < MAX_CONTACTS; i++) { mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuContact[i], (LPARAM)&mi); } } } return 0; }
static int MO_RegisterIcon( PMO_IntMenuItem pmi, void* ) { char *uname, *descr; uname = pmi->UniqName; if ( uname == NULL ) #ifdef UNICODE uname = mir_u2a(pmi->CustomName); descr = mir_u2a(pmi->mi.ptszName); #else uname = pmi->CustomName; descr = pmi->mi.pszName; #endif if ( !uname && !descr ) return FALSE; if ( !pmi->hIcolibItem ) { HICON hIcon = ImageList_GetIcon( pmi->parent->m_hMenuIcons, pmi->iconId, 0 ); char* buf = NEWSTR_ALLOCA( descr ); char sectionName[256], iconame[256]; mir_snprintf( sectionName, sizeof(sectionName), "Menu Icons/%s", pmi->parent->Name ); // remove '&' char* start = buf; while ( start ) { if (( start = strchr( start, '&' )) == NULL ) break; memmove(start,start+1,strlen(start+1)+1); if (*start!='\0') start++; else break; } mir_snprintf(iconame, sizeof(iconame), "genmenu_%s_%s", pmi->parent->Name, uname && *uname ? uname : descr); SKINICONDESC sid={0}; sid.cbSize = sizeof(sid); sid.cx = 16; sid.cy = 16; sid.pszSection = sectionName; sid.pszName = iconame; sid.pszDefaultFile = NULL; sid.pszDescription = buf; sid.hDefaultIcon = hIcon; pmi->hIcolibItem = ( HANDLE )CallService(MS_SKIN2_ADDICON, 0, (LPARAM)&sid); Safe_DestroyIcon( hIcon ); if ( hIcon = ( HICON )CallService( MS_SKIN2_GETICON, 0, (LPARAM)iconame )) { ImageList_ReplaceIcon( pmi->parent->m_hMenuIcons, pmi->iconId, hIcon ); IconLib_ReleaseIcon( hIcon, 0 ); } } #ifdef UNICODE if ( !pmi->UniqName ) mir_free( uname ); mir_free( descr ); #endif return FALSE; }
INT_PTR CSearchDialog::OnInitDialog() { HIMAGELIST himl = ImageList_Create(16,16,ILC_COLOR32|ILC_MASK,0,48); HBITMAP hBitmap = LoadBitmap(GetModuleHandle(0),MAKEINTRESOURCE(IDB_SHELLIMAGES)); ImageList_Add(himl,hBitmap,NULL); m_hDirectoryIcon = ImageList_GetIcon(himl,SHELLIMAGES_NEWTAB,ILD_NORMAL); m_hDialogIcon = ImageList_GetIcon(himl,SHELLIMAGES_SEARCH,ILD_NORMAL); SendMessage(GetDlgItem(m_hDlg,IDC_BUTTON_DIRECTORY),BM_SETIMAGE, IMAGE_ICON,reinterpret_cast<LPARAM>(m_hDirectoryIcon)); SetClassLongPtr(m_hDlg,GCLP_HICONSM,reinterpret_cast<LONG_PTR>(m_hDialogIcon)); DeleteObject(hBitmap); ImageList_Destroy(himl); HWND hListView = GetDlgItem(m_hDlg,IDC_LISTVIEW_SEARCHRESULTS); ListView_SetExtendedListViewStyleEx(hListView,LVS_EX_GRIDLINES|LVS_EX_DOUBLEBUFFER, LVS_EX_GRIDLINES|LVS_EX_DOUBLEBUFFER); HIMAGELIST himlSmall; Shell_GetImageLists(NULL,&himlSmall); ListView_SetImageList(hListView,himlSmall,LVSIL_SMALL); SetWindowTheme(hListView,L"Explorer",NULL); int i = 0; for each(auto ci in m_sdps->m_Columns) { TCHAR szTemp[128]; LoadString(GetInstance(),ci.uStringID,szTemp,SIZEOF_ARRAY(szTemp)); LVCOLUMN lvColumn; lvColumn.mask = LVCF_TEXT; lvColumn.pszText = szTemp; ListView_InsertColumn(hListView,i,&lvColumn); i++; } RECT rc; GetClientRect(hListView,&rc); ListView_SetColumnWidth(hListView,0,(1.0/3.0) * GetRectWidth(&rc)); ListView_SetColumnWidth(hListView,1,(1.80/3.0) * GetRectWidth(&rc)); UpdateListViewHeader(); lCheckDlgButton(m_hDlg,IDC_CHECK_ARCHIVE,m_sdps->m_bArchive); lCheckDlgButton(m_hDlg,IDC_CHECK_HIDDEN,m_sdps->m_bHidden); lCheckDlgButton(m_hDlg,IDC_CHECK_READONLY,m_sdps->m_bReadOnly); lCheckDlgButton(m_hDlg,IDC_CHECK_SYSTEM,m_sdps->m_bSystem); lCheckDlgButton(m_hDlg,IDC_CHECK_SEARCHSUBFOLDERS,m_sdps->m_bSearchSubFolders); lCheckDlgButton(m_hDlg,IDC_CHECK_CASEINSENSITIVE,m_sdps->m_bCaseInsensitive); lCheckDlgButton(m_hDlg,IDC_CHECK_USEREGULAREXPRESSIONS,m_sdps->m_bUseRegularExpressions); for each(auto strDirectory in m_sdps->m_SearchDirectories) { SendDlgItemMessage(m_hDlg,IDC_COMBO_DIRECTORY,CB_INSERTSTRING,static_cast<WPARAM>(-1), reinterpret_cast<LPARAM>(strDirectory.c_str())); } for each(auto strPattern in *m_sdps->m_pSearchPatterns) { SendDlgItemMessage(m_hDlg,IDC_COMBO_NAME,CB_INSERTSTRING,static_cast<WPARAM>(-1), reinterpret_cast<LPARAM>(strPattern.c_str())); } SetDlgItemText(m_hDlg,IDC_COMBO_NAME,m_sdps->m_szSearchPattern); SetDlgItemText(m_hDlg,IDC_COMBO_DIRECTORY,m_szSearchDirectory); CComboBox::CreateNew(GetDlgItem(m_hDlg,IDC_COMBO_NAME)); CComboBox::CreateNew(GetDlgItem(m_hDlg,IDC_COMBO_DIRECTORY)); if(m_sdps->m_bStateSaved) { /* These dummy values will be in use if these values have not previously been saved. */ if(m_sdps->m_iColumnWidth1 != -1 && m_sdps->m_iColumnWidth2 != -1) { ListView_SetColumnWidth(hListView,0,m_sdps->m_iColumnWidth1); ListView_SetColumnWidth(hListView,1,m_sdps->m_iColumnWidth2); } } m_sdps->RestoreDialogPosition(m_hDlg,true); SetFocus(GetDlgItem(m_hDlg,IDC_COMBO_NAME)); return FALSE; }
LRESULT CALLBACK EventAreaWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) { switch (msg) { case WM_CREATE: hwndEventFrame = hwnd; return FALSE; case WM_MEASUREITEM: { MEASUREITEMSTRUCT *lpi = (LPMEASUREITEMSTRUCT)lParam; MENUITEMINFOA mii = { 0 }; mii.cbSize = sizeof(mii); mii.fMask = MIIM_DATA | MIIM_ID; if (GetMenuItemInfoA(cfg::dat.hMenuNotify, lpi->itemID, FALSE, &mii) != 0) { if (mii.dwItemData == lpi->itemData) { lpi->itemWidth = 8 + 16; lpi->itemHeight = 0; return TRUE; } } break; } case WM_NCCALCSIZE: return FrameNCCalcSize(hwnd, DefWindowProc, wParam, lParam, wndFrameEventArea ? wndFrameEventArea->TitleBar.ShowTitleBar : 0); case WM_NCPAINT: return FrameNCPaint(hwnd, DefWindowProc, wParam, lParam, wndFrameEventArea ? wndFrameEventArea->TitleBar.ShowTitleBar : 0); case WM_DRAWITEM: { LPDRAWITEMSTRUCT dis = (LPDRAWITEMSTRUCT)lParam; if (dis->hwndItem == (HWND)cfg::dat.hMenuNotify) { MENUITEMINFOA mii = { 0 }; struct NotifyMenuItemExData *nmi = 0; int iIcon; HICON hIcon; mii.cbSize = sizeof(mii); mii.fMask = MIIM_DATA; if (GetMenuItemInfoA(cfg::dat.hMenuNotify, (UINT)dis->itemID, FALSE, &mii) != 0) { nmi = (struct NotifyMenuItemExData *) mii.dwItemData; if (nmi) { iIcon = pcli->pfnGetContactIcon(nmi->hContact); hIcon = ImageList_GetIcon(hCListImages, iIcon, ILD_NORMAL); pcli->pfnDrawMenuItem(dis, hIcon, nmi->hIcon); return TRUE; } } } break; } case WM_LBUTTONUP: if (cfg::dat.bEventAreaEnabled) SendMessage(hwnd, WM_COMMAND, MAKEWPARAM(IDC_NOTIFYBUTTON, 0), 0); break; case WM_COMMAND: if (LOWORD(wParam) == IDC_NOTIFYBUTTON) { int iSelection; struct NotifyMenuItemExData *nmi = 0; int iCount = GetMenuItemCount(cfg::dat.hMenuNotify); POINT pt; GetCursorPos(&pt); MENUITEMINFO mii = { 0 }; mii.cbSize = sizeof(mii); mii.fMask = MIIM_DATA; if (iCount > 1) iSelection = TrackPopupMenu(cfg::dat.hMenuNotify, TPM_RETURNCMD, pt.x, pt.y, 0, hwnd, NULL); else iSelection = GetMenuItemID(cfg::dat.hMenuNotify, 0); BOOL result = GetMenuItemInfo(cfg::dat.hMenuNotify, (UINT)iSelection, FALSE, &mii); if (result != 0) { nmi = (struct NotifyMenuItemExData *) mii.dwItemData; if (nmi) { CLISTEVENT *cle = MyGetEvent(iSelection); if (cle) { CLISTEVENT *cle1 = NULL; CallService(cle->pszService, (WPARAM)NULL, (LPARAM)cle); // re-obtain the pointer, it may already be invalid/point to another event if the // event we're interested in was removed by the service (nasty one...) cle1 = MyGetEvent(iSelection); if (cle1 != NULL) CallService(MS_CLIST_REMOVEEVENT, (WPARAM)cle->hContact, (LPARAM)cle->hDbEvent); } } } } break; case WM_ERASEBKGND: return TRUE; case WM_PAINT: { PAINTSTRUCT ps; HDC hdc = BeginPaint(hwnd, &ps); RECT rc, rcClient; GetClientRect(hwnd, &rc); rcClient = rc; HDC hdcMem = CreateCompatibleDC(hdc); HBITMAP hbm = CreateCompatibleBitmap(hdc, rc.right, rc.bottom); HBITMAP hbmold = reinterpret_cast<HBITMAP>(SelectObject(hdcMem, hbm)); SetBkMode(hdcMem, TRANSPARENT); HFONT hFontOld = 0; if (cfg::clcdat) { int height; hFontOld = ChangeToFont(hdcMem, cfg::clcdat, FONTID_EVENTAREA, &height); } if (cfg::dat.bWallpaperMode) SkinDrawBg(hwnd, hdcMem); StatusItems_t *item = arStatusItems[ID_EXTBKEVTAREA - ID_STATUS_OFFLINE]; if (item->IGNORED) FillRect(hdcMem, &rc, GetSysColorBrush(COLOR_3DFACE)); else { rc.top += item->MARGIN_TOP; rc.bottom -= item->MARGIN_BOTTOM; rc.left += item->MARGIN_LEFT; rc.right -= item->MARGIN_RIGHT; DrawAlpha(hdcMem, &rc, item->COLOR, item->ALPHA, item->COLOR2, item->COLOR2_TRANSPARENT, item->GRADIENT, item->CORNER, item->BORDERSTYLE, item->imageItem); SetTextColor(hdcMem, item->TEXTCOLOR); } LONG dwLeft = rc.left; PaintNotifyArea(hdcMem, &rc); if (cfg::dat.dwFlags & CLUI_FRAME_EVENTAREASUNKEN) { rc.left = dwLeft; InflateRect(&rc, -2, -2); DrawEdge(hdcMem, &rc, BDR_SUNKENOUTER, BF_RECT); } BitBlt(hdc, 0, 0, rcClient.right, rcClient.bottom, hdcMem, 0, 0, SRCCOPY); SelectObject(hdcMem, hbmold); if (hFontOld) SelectObject(hdcMem, hFontOld); DeleteObject(hbm); DeleteDC(hdcMem); ps.fErase = FALSE; EndPaint(hwnd, &ps); } return 0; default: return DefWindowProc(hwnd, msg, wParam, lParam); } return TRUE; }
static void PaintWorker(MButtonCtrl *ctl, HDC hdcPaint) { if (hdcPaint) { HDC hdcMem; HBITMAP hbmMem; HDC hOld; RECT rcClient; GetClientRect(ctl->hwnd, &rcClient); hdcMem = CreateCompatibleDC(hdcPaint); hbmMem = CreateCompatibleBitmap(hdcPaint, rcClient.right-rcClient.left, rcClient.bottom-rcClient.top); hOld = ( HDC )SelectObject(hdcMem, hbmMem); // If its a push button, check to see if it should stay pressed if (ctl->pushBtn && ctl->pbState) ctl->stateId = PBS_PRESSED; // Draw the flat button if (ctl->flatBtn) { if (ctl->hThemeToolbar) { int state = IsWindowEnabled(ctl->hwnd)?(ctl->stateId==PBS_NORMAL&&ctl->defbutton?PBS_DEFAULTED:ctl->stateId):PBS_DISABLED; if (isThemeBackgroundPartiallyTransparent(ctl->hThemeToolbar, TP_BUTTON, TBStateConvert2Flat(state))) { drawThemeParentBackground(ctl->hwnd, hdcMem, &rcClient); } drawThemeBackground(ctl->hThemeToolbar, hdcMem, TP_BUTTON, TBStateConvert2Flat(state), &rcClient, &rcClient); } else { HBRUSH hbr; if (ctl->stateId==PBS_PRESSED||ctl->stateId==PBS_HOT) hbr = GetSysColorBrush(COLOR_3DLIGHT); else { HWND hwndParent = GetParent(ctl->hwnd); HDC dc = GetDC(hwndParent); HBRUSH oldBrush = (HBRUSH)GetCurrentObject( dc, OBJ_BRUSH ); hbr = (HBRUSH)SendMessage(hwndParent, WM_CTLCOLORDLG, (WPARAM)dc, (LPARAM)hwndParent); SelectObject(dc,oldBrush); ReleaseDC(hwndParent,dc); } if (hbr) { FillRect(hdcMem, &rcClient, hbr); DeleteObject(hbr); } if (ctl->stateId==PBS_HOT||ctl->focus) { if (ctl->pbState) DrawEdge(hdcMem,&rcClient, EDGE_ETCHED,BF_RECT|BF_SOFT); else DrawEdge(hdcMem,&rcClient, BDR_RAISEDOUTER,BF_RECT|BF_SOFT|BF_FLAT); } else if (ctl->stateId==PBS_PRESSED) DrawEdge(hdcMem, &rcClient, BDR_SUNKENOUTER,BF_RECT|BF_SOFT); } } else { // Draw background/border if (ctl->hThemeButton) { int state = IsWindowEnabled(ctl->hwnd)?(ctl->stateId==PBS_NORMAL&&ctl->defbutton?PBS_DEFAULTED:ctl->stateId):PBS_DISABLED; if (isThemeBackgroundPartiallyTransparent(ctl->hThemeButton, BP_PUSHBUTTON, state)) { drawThemeParentBackground(ctl->hwnd, hdcMem, &rcClient); } drawThemeBackground(ctl->hThemeButton, hdcMem, BP_PUSHBUTTON, state, &rcClient, &rcClient); } else { UINT uState = DFCS_BUTTONPUSH|((ctl->stateId==PBS_HOT)?DFCS_HOT:0)|((ctl->stateId == PBS_PRESSED)?DFCS_PUSHED:0); if (ctl->defbutton&&ctl->stateId==PBS_NORMAL) uState |= DLGC_DEFPUSHBUTTON; DrawFrameControl(hdcMem, &rcClient, DFC_BUTTON, uState); } // Draw focus rectangle if button has focus if (ctl->focus) { RECT focusRect = rcClient; InflateRect(&focusRect, -3, -3); DrawFocusRect(hdcMem, &focusRect); } } // If we have an icon or a bitmap, ignore text and only draw the image on the button if (ctl->hIcon) { int ix = (rcClient.right-rcClient.left)/2 - (GetSystemMetrics(SM_CXSMICON)/2); int iy = (rcClient.bottom-rcClient.top)/2 - (GetSystemMetrics(SM_CYSMICON)/2); if (ctl->stateId == PBS_PRESSED) { ix++; iy++; } { HIMAGELIST hImageList; HICON hIconNew; hImageList = ImageList_Create(GetSystemMetrics(SM_CXSMICON),GetSystemMetrics(SM_CYSMICON), IsWinVerXPPlus()? ILC_COLOR32 | ILC_MASK : ILC_COLOR16 | ILC_MASK, 1, 0); ImageList_AddIcon(hImageList, ctl->hIcon); hIconNew = ImageList_GetIcon(hImageList, 0, ILD_NORMAL); DrawState(hdcMem,NULL,NULL,(LPARAM)hIconNew,0,ix,iy,GetSystemMetrics(SM_CXSMICON),GetSystemMetrics(SM_CYSMICON),IsWindowEnabled(ctl->hwnd)?DST_ICON|DSS_NORMAL:DST_ICON|DSS_DISABLED); ImageList_RemoveAll(hImageList); ImageList_Destroy(hImageList); DestroyIcon(hIconNew); } } else if (ctl->hBitmap) { BITMAP bminfo; int ix,iy; GetObject(ctl->hBitmap, sizeof(bminfo), &bminfo); ix = (rcClient.right-rcClient.left)/2 - (bminfo.bmWidth/2); iy = (rcClient.bottom-rcClient.top)/2 - (bminfo.bmHeight/2); if (ctl->stateId == PBS_PRESSED) { ix++; iy++; } DrawState(hdcMem,NULL,NULL,(LPARAM)ctl->hBitmap,0,ix,iy,bminfo.bmWidth,bminfo.bmHeight,IsWindowEnabled(ctl->hwnd)?DST_BITMAP:DST_BITMAP|DSS_DISABLED); } else if (GetWindowTextLength(ctl->hwnd)) { // Draw the text and optinally the arrow TCHAR szText[MAX_PATH]; SIZE sz; RECT rcText; HFONT hOldFont; CopyRect(&rcText, &rcClient); GetWindowText(ctl->hwnd, szText, SIZEOF(szText)); SetBkMode(hdcMem, TRANSPARENT); hOldFont = (HFONT)SelectObject(hdcMem, ctl->hFont); // XP w/themes doesn't used the glossy disabled text. Is it always using COLOR_GRAYTEXT? Seems so. SetTextColor(hdcMem, IsWindowEnabled(ctl->hwnd)||!ctl->hThemeButton?GetSysColor(COLOR_BTNTEXT):GetSysColor(COLOR_GRAYTEXT)); GetTextExtentPoint32(hdcMem, szText, lstrlen(szText), &sz); if (ctl->cHot) { SIZE szHot; GetTextExtentPoint32 (hdcMem, _T("&"), 1, &szHot); sz.cx -= szHot.cx; } if (ctl->arrow) { DrawState(hdcMem,NULL,NULL,(LPARAM)ctl->arrow,0,rcClient.right-rcClient.left-5-GetSystemMetrics(SM_CXSMICON)+(!ctl->hThemeButton&&ctl->stateId==PBS_PRESSED?1:0),(rcClient.bottom-rcClient.top)/2-GetSystemMetrics(SM_CYSMICON)/2+(!ctl->hThemeButton&&ctl->stateId==PBS_PRESSED?1:0),GetSystemMetrics(SM_CXSMICON),GetSystemMetrics(SM_CYSMICON),IsWindowEnabled(ctl->hwnd)?DST_ICON:DST_ICON|DSS_DISABLED); } SelectObject(hdcMem, ctl->hFont); DrawState(hdcMem,NULL,NULL,(LPARAM)szText,0,(rcText.right-rcText.left-sz.cx)/2+(!ctl->hThemeButton&&ctl->stateId==PBS_PRESSED?1:0),ctl->hThemeButton?(rcText.bottom-rcText.top-sz.cy)/2:(rcText.bottom-rcText.top-sz.cy)/2-(ctl->stateId==PBS_PRESSED?0:1),sz.cx,sz.cy,IsWindowEnabled(ctl->hwnd)||ctl->hThemeButton?DST_PREFIXTEXT|DSS_NORMAL:DST_PREFIXTEXT|DSS_DISABLED); SelectObject(hdcMem, hOldFont); } BitBlt(hdcPaint, 0, 0, rcClient.right-rcClient.left, rcClient.bottom-rcClient.top, hdcMem, 0, 0, SRCCOPY); SelectObject(hdcMem, hOld); DeleteObject(hbmMem); DeleteDC(hdcMem); } }
int PrebuildContactMenu(WPARAM wParam, LPARAM lParam) { HANDLE hContact = (HANDLE)wParam; CLISTMENUITEM mi = {0}; mi.cbSize = sizeof(CLISTMENUITEM); if(MetaEnabled()) { if(IsSubcontact(hContact)) { mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuAdd, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuConvert, (LPARAM)&mi); mi.flags = CMIM_FLAGS; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDefault, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuRemove, (LPARAM)&mi); } else if(IsMetacontact(hContact)) { GetCursorPos(&menuMousePoint); mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuAdd, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuConvert, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDefault, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuRemove, (LPARAM)&mi); if(!metaMap.exists(hContact)) { PUShowMessage("No such meta!", SM_WARNING); return 0; } // show subcontact menu items mi.flags = CMIM_FLAGS | CMIM_NAME | CMIM_ICON | CMIF_TCHAR; HIMAGELIST il = (HIMAGELIST)CallService(MS_CLIST_GETICONSIMAGELIST, 0, 0); SubcontactList::Iterator i = metaMap[hContact].start(); int count = 0; TCHAR buff[31]; while(i.has_val()) { // limit names to 30 chars mir_sntprintf(buff, 31, _T("%s"), ContactName(i.val().handle())); mi.ptszName = buff; mi.hIcon = ImageList_GetIcon(il, (int)CallService(MS_CLIST_GETCONTACTICON, (WPARAM)i.val().handle(), 0), 0); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuContact[count], (LPARAM)&mi); i.next(); count++; } mi.flags = CMIM_FLAGS | CMIF_HIDDEN; for(;count < MAX_SUBCONTACTS; count++) CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuContact[count], (LPARAM)&mi); // show hide nudge menu item // wParam = char *szProto // lParam = BOOL show #define MS_NUDGE_SHOWMENU "NudgeShowMenu" { char serviceFunc[256]; hContact = Meta_GetActive((HANDLE)wParam); mir_snprintf(serviceFunc, 256, "%s/SendNudge", ContactProto(hContact)); CallService(MS_NUDGE_SHOWMENU, (WPARAM)MODULE, (LPARAM)ServiceExists(serviceFunc)); } } else { mi.flags = CMIM_FLAGS; if(metaMap.size()) CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuAdd, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuConvert, (LPARAM)&mi); mi.flags = CMIM_FLAGS | CMIF_HIDDEN; if(!metaMap.size()) CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuAdd, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuRemove, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDefault, (LPARAM)&mi); } } else { mi.flags = CMIM_FLAGS | CMIF_HIDDEN; CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuAdd, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuConvert, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuDefault, (LPARAM)&mi); CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hMenuRemove, (LPARAM)&mi); } return 0; }
void InitSubGroupMenus(void) { CreateServiceFunction("CLISTMENUSSubGroup/ExecService", SubGroupMenuExecService); CreateServiceFunction("CLISTMENUSSubGroup/FreeOwnerDataSubGroupMenu", FreeOwnerDataSubGroupMenu); CreateServiceFunction("CLISTMENUSSubGroup/SubGroupMenuonAddService", SubGroupMenuonAddService); CreateServiceFunction("CLISTMENUSSubGroup/GroupMenuExecProxy", GroupMenuExecProxy); CreateServiceFunction("CList/AddSubGroupMenuItem", AddSubGroupMenuItem); CreateServiceFunction(MS_CLIST_REMOVESUBGROUPMENUITEM, RemoveSubGroupMenuItem); CreateServiceFunction(MS_CLIST_MENUBUILDSUBGROUP, BuildSubGroupMenu); hPreBuildSubGroupMenuEvent = CreateHookableEvent(ME_CLIST_PREBUILDSUBGROUPMENU); HookEvent(ME_CLIST_PREBUILDSUBGROUPMENU, OnBuildSubGroupMenu); //SubGroup menu hSubGroupMenuObject = MO_CreateMenuObject("SubGroupMenu", LPGEN("Subgroup menu"), 0, "CLISTMENUSSubGroup/ExecService"); MO_SetMenuObjectParam(hSubGroupMenuObject, OPT_USERDEFINEDITEMS, TRUE); MO_SetMenuObjectParam(hSubGroupMenuObject, OPT_MENUOBJECT_SET_FREE_SERVICE, "CLISTMENUSSubGroup/FreeOwnerDataSubGroupMenu"); MO_SetMenuObjectParam(hSubGroupMenuObject, OPT_MENUOBJECT_SET_ONADD_SERVICE, "CLISTMENUSSubGroup/SubGroupMenuonAddService"); //add exit command to menu GroupMenuParam gmp; CLISTMENUITEM mi = { sizeof(mi) }; mi.position = 1000; mi.hIcon = ImageList_GetIcon(hCListImages, NewGroupIconidx, 0); mi.pszService = "CLISTMENUSSubGroup/GroupMenuExecProxy"; mi.pszName = LPGEN("&New subgroup"); gmp.lParam = 0; gmp.wParam = POPUP_NEWSUBGROUP; hNewSubGroupMenuItem = (HGENMENU)AddSubGroupMenuItem((WPARAM)&gmp, (LPARAM)&mi); memset(&mi, 0, sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 1001; mi.hIcon = NULL; mi.pszService = "CLISTMENUSSubGroup/GroupMenuExecProxy"; mi.pszName = LPGEN("&Hide offline users in here"); gmp.lParam = 0; gmp.wParam = POPUP_GROUPHIDEOFFLINE; hHideOfflineUsersHereMenuItem = (HGENMENU)AddSubGroupMenuItem((WPARAM)&gmp, (LPARAM)&mi); memset(&mi, 0, sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 900001; mi.icolibItem = LoadSkinnedIconHandle(SKINICON_OTHER_RENAME); //LoadIcon(GetModuleHandle(NULL),MAKEINTRESOURCE(IDI_RENAME)); mi.pszService = "CLISTMENUSSubGroup/GroupMenuExecProxy"; mi.pszName = LPGEN("&Rename group"); gmp.lParam = 0; gmp.wParam = POPUP_RENAMEGROUP; AddSubGroupMenuItem((WPARAM)&gmp, (LPARAM)&mi); memset(&mi, 0, sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 900002; mi.icolibItem = LoadSkinnedIconHandle(SKINICON_OTHER_DELETE); //LoadIcon(GetModuleHandle(NULL),MAKEINTRESOURCE(IDI_DELETE)); mi.pszService = "CLISTMENUSSubGroup/GroupMenuExecProxy"; mi.pszName = LPGEN("&Delete group"); gmp.lParam = 0; gmp.wParam = POPUP_DELETEGROUP; AddSubGroupMenuItem((WPARAM)&gmp, (LPARAM)&mi); }
/************************************************************************* * SHGetFileInfoW [SHELL32.@] * */ DWORD_PTR WINAPI SHGetFileInfoW(LPCWSTR path,DWORD dwFileAttributes, SHFILEINFOW *psfi, UINT sizeofpsfi, UINT flags ) { WCHAR szLocation[MAX_PATH], szFullPath[MAX_PATH]; int iIndex; DWORD_PTR ret = TRUE; DWORD dwAttributes = 0; IShellFolder * psfParent = NULL; IExtractIconW * pei = NULL; LPITEMIDLIST pidlLast = NULL, pidl = NULL; HRESULT hr = S_OK; BOOL IconNotYetLoaded=TRUE; UINT uGilFlags = 0; TRACE("%s fattr=0x%x sfi=%p(attr=0x%08x) size=0x%x flags=0x%x\n", (flags & SHGFI_PIDL)? "pidl" : debugstr_w(path), dwFileAttributes, psfi, psfi->dwAttributes, sizeofpsfi, flags); if (!path) return FALSE; /* windows initializes these values regardless of the flags */ if (psfi != NULL) { psfi->szDisplayName[0] = '\0'; psfi->szTypeName[0] = '\0'; psfi->iIcon = 0; } if (!(flags & SHGFI_PIDL)) { /* SHGetFileInfo should work with absolute and relative paths */ if (PathIsRelativeW(path)) { GetCurrentDirectoryW(MAX_PATH, szLocation); PathCombineW(szFullPath, szLocation, path); } else { lstrcpynW(szFullPath, path, MAX_PATH); } } if (flags & SHGFI_EXETYPE) { if (flags != SHGFI_EXETYPE) return 0; return shgfi_get_exe_type(szFullPath); } /* * psfi is NULL normally to query EXE type. If it is NULL, none of the * below makes sense anyway. Windows allows this and just returns FALSE */ if (psfi == NULL) return FALSE; /* * translate the path into a pidl only when SHGFI_USEFILEATTRIBUTES * is not specified. * The pidl functions fail on not existing file names */ if (flags & SHGFI_PIDL) { pidl = ILClone((LPCITEMIDLIST)path); } else if (!(flags & SHGFI_USEFILEATTRIBUTES)) { hr = SHILCreateFromPathW(szFullPath, &pidl, &dwAttributes); } if ((flags & SHGFI_PIDL) || !(flags & SHGFI_USEFILEATTRIBUTES)) { /* get the parent shellfolder */ if (pidl) { hr = SHBindToParent( pidl, &IID_IShellFolder, (LPVOID*)&psfParent, (LPCITEMIDLIST*)&pidlLast ); if (SUCCEEDED(hr)) pidlLast = ILClone(pidlLast); ILFree(pidl); } else { ERR("pidl is null!\n"); return FALSE; } } /* get the attributes of the child */ if (SUCCEEDED(hr) && (flags & SHGFI_ATTRIBUTES)) { if (!(flags & SHGFI_ATTR_SPECIFIED)) { psfi->dwAttributes = 0xffffffff; } if (psfParent) IShellFolder_GetAttributesOf( psfParent, 1, (LPCITEMIDLIST*)&pidlLast, &(psfi->dwAttributes) ); } /* get the displayname */ if (SUCCEEDED(hr) && (flags & SHGFI_DISPLAYNAME)) { if (flags & SHGFI_USEFILEATTRIBUTES && !(flags & SHGFI_PIDL)) { lstrcpyW (psfi->szDisplayName, PathFindFileNameW(szFullPath)); } else { STRRET str; hr = IShellFolder_GetDisplayNameOf( psfParent, pidlLast, SHGDN_INFOLDER, &str); StrRetToStrNW (psfi->szDisplayName, MAX_PATH, &str, pidlLast); } } /* get the type name */ if (SUCCEEDED(hr) && (flags & SHGFI_TYPENAME)) { static const WCHAR szFile[] = { 'F','i','l','e',0 }; static const WCHAR szDashFile[] = { '-','f','i','l','e',0 }; if (!(flags & SHGFI_USEFILEATTRIBUTES) || (flags & SHGFI_PIDL)) { char ftype[80]; _ILGetFileType(pidlLast, ftype, 80); MultiByteToWideChar(CP_ACP, 0, ftype, -1, psfi->szTypeName, 80 ); } else { if (dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) strcatW (psfi->szTypeName, szFile); else { WCHAR sTemp[64]; lstrcpyW(sTemp,PathFindExtensionW(szFullPath)); if (!( HCR_MapTypeToValueW(sTemp, sTemp, 64, TRUE) && HCR_MapTypeToValueW(sTemp, psfi->szTypeName, 80, FALSE ))) { lstrcpynW (psfi->szTypeName, sTemp, 64); strcatW (psfi->szTypeName, szDashFile); } } } } /* ### icons ###*/ if (flags & SHGFI_OPENICON) uGilFlags |= GIL_OPENICON; if (flags & SHGFI_LINKOVERLAY) uGilFlags |= GIL_FORSHORTCUT; else if ((flags&SHGFI_ADDOVERLAYS) || (flags&(SHGFI_ICON|SHGFI_SMALLICON))==SHGFI_ICON) { if (SHELL_IsShortcut(pidlLast)) uGilFlags |= GIL_FORSHORTCUT; } if (flags & SHGFI_OVERLAYINDEX) FIXME("SHGFI_OVERLAYINDEX unhandled\n"); if (flags & SHGFI_SELECTED) FIXME("set icon to selected, stub\n"); if (flags & SHGFI_SHELLICONSIZE) FIXME("set icon to shell size, stub\n"); /* get the iconlocation */ if (SUCCEEDED(hr) && (flags & SHGFI_ICONLOCATION )) { UINT uDummy,uFlags; if (flags & SHGFI_USEFILEATTRIBUTES && !(flags & SHGFI_PIDL)) { if (dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) { lstrcpyW(psfi->szDisplayName, swShell32Name); psfi->iIcon = -IDI_SHELL_FOLDER; } else { WCHAR* szExt; static const WCHAR p1W[] = {'%','1',0}; WCHAR sTemp [MAX_PATH]; szExt = PathFindExtensionW(szFullPath); TRACE("szExt=%s\n", debugstr_w(szExt)); if ( szExt && HCR_MapTypeToValueW(szExt, sTemp, MAX_PATH, TRUE) && HCR_GetDefaultIconW(sTemp, sTemp, MAX_PATH, &psfi->iIcon)) { if (lstrcmpW(p1W, sTemp)) strcpyW(psfi->szDisplayName, sTemp); else { /* the icon is in the file */ strcpyW(psfi->szDisplayName, szFullPath); } } else ret = FALSE; } } else { hr = IShellFolder_GetUIObjectOf(psfParent, 0, 1, (LPCITEMIDLIST*)&pidlLast, &IID_IExtractIconW, &uDummy, (LPVOID*)&pei); if (SUCCEEDED(hr)) { hr = IExtractIconW_GetIconLocation(pei, uGilFlags, szLocation, MAX_PATH, &iIndex, &uFlags); if (uFlags & GIL_NOTFILENAME) ret = FALSE; else { lstrcpyW (psfi->szDisplayName, szLocation); psfi->iIcon = iIndex; } IExtractIconW_Release(pei); } } } /* get icon index (or load icon)*/ if (SUCCEEDED(hr) && (flags & (SHGFI_ICON | SHGFI_SYSICONINDEX))) { if (flags & SHGFI_USEFILEATTRIBUTES && !(flags & SHGFI_PIDL)) { WCHAR sTemp [MAX_PATH]; WCHAR * szExt; int icon_idx=0; lstrcpynW(sTemp, szFullPath, MAX_PATH); if (dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) psfi->iIcon = SIC_GetIconIndex(swShell32Name, -IDI_SHELL_FOLDER, 0); else { static const WCHAR p1W[] = {'%','1',0}; psfi->iIcon = 0; szExt = PathFindExtensionW(sTemp); if ( szExt && HCR_MapTypeToValueW(szExt, sTemp, MAX_PATH, TRUE) && HCR_GetDefaultIconW(sTemp, sTemp, MAX_PATH, &icon_idx)) { if (!lstrcmpW(p1W,sTemp)) /* icon is in the file */ strcpyW(sTemp, szFullPath); if (flags & SHGFI_SYSICONINDEX) { psfi->iIcon = SIC_GetIconIndex(sTemp,icon_idx,0); if (psfi->iIcon == -1) psfi->iIcon = 0; } else { UINT ret; if (flags & SHGFI_SMALLICON) ret = PrivateExtractIconsW( sTemp,icon_idx, GetSystemMetrics( SM_CXSMICON ), GetSystemMetrics( SM_CYSMICON ), &psfi->hIcon, 0, 1, 0); else ret = PrivateExtractIconsW( sTemp, icon_idx, GetSystemMetrics( SM_CXICON), GetSystemMetrics( SM_CYICON), &psfi->hIcon, 0, 1, 0); if (ret != 0 && ret != (UINT)-1) { IconNotYetLoaded=FALSE; psfi->iIcon = icon_idx; } } } } } else { if (!(PidlToSicIndex(psfParent, pidlLast, !(flags & SHGFI_SMALLICON), uGilFlags, &(psfi->iIcon)))) { ret = FALSE; } } if (ret && (flags & SHGFI_SYSICONINDEX)) { if (flags & SHGFI_SMALLICON) ret = (DWORD_PTR) ShellSmallIconList; else ret = (DWORD_PTR) ShellBigIconList; } } /* icon handle */ if (SUCCEEDED(hr) && (flags & SHGFI_ICON) && IconNotYetLoaded) { if (flags & SHGFI_SMALLICON) psfi->hIcon = ImageList_GetIcon( ShellSmallIconList, psfi->iIcon, ILD_NORMAL); else psfi->hIcon = ImageList_GetIcon( ShellBigIconList, psfi->iIcon, ILD_NORMAL); } if (flags & ~SHGFI_KNOWN_FLAGS) FIXME("unknown flags %08x\n", flags & ~SHGFI_KNOWN_FLAGS); if (psfParent) IShellFolder_Release(psfParent); if (hr != S_OK) ret = FALSE; SHFree(pidlLast); TRACE ("icon=%p index=0x%08x attr=0x%08x name=%s type=%s ret=0x%08lx\n", psfi->hIcon, psfi->iIcon, psfi->dwAttributes, debugstr_w(psfi->szDisplayName), debugstr_w(psfi->szTypeName), ret); return ret; }
void MenuItem::Paint(HDC hDC) { RECT rect; COLORREF cr0 = (COLORREF)-1; bool lit = false; StyleItem *pSI = &mStyle.MenuFrame; if (m_bActive && 0 == (m_isNOP & (MI_NOP_TEXT | MI_NOP_SEP)) && (0 == (m_isNOP & MI_NOP_DISABLED) || m_pSubMenu)) { // draw hilite bar GetItemRect(&rect); pSI = &mStyle.MenuHilite; MakeStyleGradient(hDC, &rect, pSI, pSI->bordered); cr0 = SetTextColor(hDC, pSI->TextColor); lit = true; } else if (m_isNOP & MI_NOP_DISABLED) { cr0 = SetTextColor(hDC, mStyle.MenuFrame.disabledColor); } //dbg_printf("Menu separator style is: %s",Settings_menuSeparatorStyle); // draw separator if (m_isNOP & MI_NOP_LINE) { int x, y = m_nTop + m_nHeight / 2; // Noccy: Looks like we have to remove some pixels here to prevent it from overwriting the right border. int left = m_nLeft + ((Settings_menuFullSeparatorWidth)?1:mStyle.MenuSepMargin) - 1; int right = m_nLeft + m_nWidth - ((Settings_menuFullSeparatorWidth)?1:mStyle.MenuSepMargin); // int dist = (m_nWidth + 1) / 2 - ((Settings_menuFullSeparatorWidth==true)?mStyle.MenuFrame.borderWidth:mStyle.MenuSepMargin); int dist = (m_nWidth+1) / 2 - ((Settings_menuFullSeparatorWidth)?1:mStyle.MenuSepMargin); COLORREF c = mStyle.MenuSepColor; COLORREF cs = pSI->ShadowColor; if (pSI->ShadowXY) { int yS = y + pSI->ShadowY; int leftS = left + pSI->ShadowX; int rightS = right + pSI->ShadowX; if (0 == stricmp(Settings_menuSeparatorStyle,"gradient")) { // Gradient shadow for (x = 0; x <= dist; ++x) { int pos, hue = x * 255 / dist; pos = leftS + x; SetPixel(hDC, pos, yS, mixcolors(cs, GetPixel(hDC, pos, y), hue)); pos = rightS - x; SetPixel(hDC, pos, yS, mixcolors(cs, GetPixel(hDC, pos, y), hue)); } } else if (0 == stricmp(Settings_menuSeparatorStyle,"flat")) { // Flat shadow for (x = 0; x <= dist; ++x) { int pos; pos = leftS + x; SetPixel(hDC, pos, yS, cs); pos = rightS - x; SetPixel(hDC, pos, yS, cs); } } else if (0 == stricmp(Settings_menuSeparatorStyle,"bevel")) { // Bevel shadow is simply none... } } if (0 == stricmp(Settings_menuSeparatorStyle,"gradient")) { for (x = 0; x <= dist; ++x) { int pos, hue = x * 255 / dist; pos = left + x; SetPixel(hDC, pos, y, mixcolors(c, GetPixel(hDC, pos, y), hue)); pos = right - x; SetPixel(hDC, pos, y, mixcolors(c, GetPixel(hDC, pos, y), hue)); } } else if (0 == stricmp(Settings_menuSeparatorStyle,"flat")) { for (x = 0; x <= dist; ++x) { int pos; //, hue = x * 255 / dist; pos = left + x; SetPixel(hDC, pos, y, c); pos = right - x; SetPixel(hDC, pos, y, c); } } else if (0 == stricmp(Settings_menuSeparatorStyle,"bevel")) { for (x = 0; x <= dist; ++x) { int pos; pos = left + x; SetPixel(hDC, pos, y, mixcolors(0x00000000, GetPixel(hDC, pos, y), 160)); pos = right - x; SetPixel(hDC, pos, y, mixcolors(0x00000000, GetPixel(hDC, pos, y), 160)); pos = left + x; SetPixel(hDC, pos, y+1, mixcolors(0x00FFFFFF, GetPixel(hDC, pos, y+1), 160)); pos = right - x; SetPixel(hDC, pos, y+1, mixcolors(0x00FFFFFF, GetPixel(hDC, pos, y+1), 160)); } } } int iconSize = m_pMenu->m_iconSize; if (-2 == iconSize) iconSize = MenuInfo.nIconSize; GetTextRect(&rect, iconSize); // [load and ]draw menu item icon if (iconSize) { bool bSmallIcon = (16 >= iconSize); // load menu item icon if (NULL == m_hIcon || bSmallIcon != m_bSmallIcon) { DestroyIcon(m_hIcon), m_hIcon = NULL; m_bSmallIcon = bSmallIcon; switch (m_iconMode) { case IM_PIDL: { const _ITEMIDLIST *pidl = (MENUITEM_ID_SF == m_ItemID) ? ((SpecialFolderItem*)this)->check_pidl() : m_pidl; if (pidl) { SHFILEINFO sfi; HIMAGELIST sysimgl = (HIMAGELIST)SHGetFileInfo((LPCSTR)pidl, 0, &sfi, sizeof(SHFILEINFO), SHGFI_PIDL | SHGFI_SYSICONINDEX | (bSmallIcon ? SHGFI_SMALLICON : SHGFI_LARGEICON)); if (sysimgl) m_hIcon = ImageList_GetIcon(sysimgl, sfi.iIcon, ILD_NORMAL); } } break; case IM_TASK: { const struct tasklist *tl = (struct tasklist *)m_im_stuff; m_hIcon = CopyIcon(bSmallIcon ? tl->icon : tl->icon_big); } break; case IM_PATH: char *icon = (char *)m_im_stuff; char *path = strrchr(icon, ','); int idx; if (path) idx = atoi(path + 1), *path = 0; else idx = 0; if (bSmallIcon) ExtractIconEx(icon, idx, NULL, &m_hIcon, 1); else ExtractIconEx(icon, idx, &m_hIcon, NULL, 1); if (path) *path = ','; break; } } // draw menu item icon if (m_hIcon) { int top = rect.top + (m_nHeight - iconSize) / 2; int adjust = (MenuInfo.nItemIndent[iconSize] - iconSize) / 2; int left = ((DT_LEFT == FolderItem::m_nBulletPosition) ? rect.right : m_nLeft) + adjust; drawIco(left, top, iconSize, m_hIcon, hDC, !m_bActive, Settings_menuIconSaturation, Settings_menuIconHue); } } /* Noccy: Added DT_NOPREFIX to BBDrawText to prevent ampersand (&) to be interpreted as a hotkey. Note: Reverted. */ // draw menu item text const char *title = GetDisplayString(); if (0 == (m_ItemID & (~MENUITEM_ID_CI & (MENUITEM_ID_CIInt|MENUITEM_ID_CIStr))) || Settings_menusBroamMode) BBDrawText(hDC, title, -1, &rect, mStyle.MenuFrame.Justify | DT_MENU_STANDARD, pSI); else if (m_ItemID != MENUITEM_ID_CIStr) BBDrawText(hDC, title, -1, &rect, DT_CENTER | DT_MENU_STANDARD, pSI); // set back previous textColor if ((COLORREF)-1 != cr0) SetTextColor(hDC, cr0); if (m_isChecked) // draw check-mark { pSI = &mStyle.MenuHilite; bool pr = pSI->parentRelative; if (lit != pr) pSI = &mStyle.MenuFrame; int x, y = m_nTop + m_nHeight / 2; if ((FolderItem::m_nBulletPosition == DT_RIGHT) == (0 == (MENUITEM_ID_FOLDER & m_ItemID))) x = m_nLeft + m_nWidth - MenuInfo.nItemIndent[iconSize] / 2 - 1; else x = m_nLeft + MenuInfo.nItemIndent[iconSize] / 2; const int r = 3; rect.left = x - r; rect.right = x + r; rect.top = y - r; rect.bottom = y + r; if (pr) MakeGradient(hDC, rect, B_SOLID, pSI->TextColor, 0, false, BEVEL_FLAT, 0, 0, 0, 0); else MakeStyleGradient(hDC, &rect, pSI, false); } }
void InitGroupMenus(void) { HICON hicon = LoadIconFromExternalFile("clisticons.dll",2,TRUE,TRUE,"NewGroup","Contact list","New Group",-IDI_NEWGROUP2,0); NewGroupIconidx = ImageList_AddIcon(hCListImages,hicon ); CreateServiceFunction("CLISTMENUSGroup/ExecService",GroupMenuExecService); CreateServiceFunction("CLISTMENUSGroup/FreeOwnerDataGroupMenu",FreeOwnerDataGroupMenu); CreateServiceFunction("CLISTMENUSGroup/GroupMenuonAddService",GroupMenuonAddService); CreateServiceFunction("CLISTMENUSGroup/HideGroupsHelper",HideGroupsHelper); CreateServiceFunction("CLISTMENUSGroup/UseGroupsHelper",UseGroupsHelper); CreateServiceFunction("CLISTMENUSGroup/HideOfflineRootHelper",HideOfflineRootHelper); CreateServiceFunction("CList/AddGroupMenuItem",AddGroupMenuItem); CreateServiceFunction(MS_CLIST_REMOVEGROUPMENUITEM,RemoveGroupMenuItem); CreateServiceFunction(MS_CLIST_MENUBUILDGROUP,BuildGroupMenu); hPreBuildGroupMenuEvent = CreateHookableEvent(ME_CLIST_PREBUILDGROUPMENU); HookEvent(ME_CLIST_PREBUILDGROUPMENU,OnBuildGroupMenu); InitSubGroupMenus(); // Group menu hGroupMenuObject = MO_CreateMenuObject("GroupMenu", LPGEN("Group menu"), 0, "CLISTMENUSGroup/ExecService"); MO_SetMenuObjectParam(hGroupMenuObject, OPT_USERDEFINEDITEMS, TRUE); MO_SetMenuObjectParam(hGroupMenuObject, OPT_MENUOBJECT_SET_FREE_SERVICE, "CLISTMENUSGroup/FreeOwnerDataGroupMenu"); MO_SetMenuObjectParam(hGroupMenuObject, OPT_MENUOBJECT_SET_ONADD_SERVICE, "CLISTMENUSGroup/GroupMenuonAddService"); { //add exit command to menu GroupMenuParam gmp; CLISTMENUITEM mi = { sizeof(mi) }; mi.position = 1900000; mi.pszService = "CloseAction"; mi.pszName = LPGEN("E&xit"); AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 500; mi.pszService = MS_CLIST_SHOWHIDE; mi.pszName = LPGEN("&Hide/Show"); hHideShowMainMenuItem = (HANDLE)AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 200000; mi.hIcon = LoadIcon(GetModuleHandle(NULL), MAKEINTRESOURCE(IDI_FINDUSER)); mi.pszService = "FindAdd/FindAddCommand"; mi.pszName = LPGEN("&Find/Add Contacts..."); AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 300000; mi.pszService = ""; mi.pszName = LPGEN("&Main menu"); hGroupMainMenuItemProxy = (HANDLE)AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 300100; mi.pszService = ""; mi.pszName = LPGEN("&Status"); hGroupStatusMenuItemProxy = (HANDLE)AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 400000; mi.hIcon = LoadIcon(GetModuleHandle(NULL),MAKEINTRESOURCE(IDI_OPTIONS)); mi.pszService = "Options/OptionsCommand"; mi.pszName = LPGEN("&Options..."); AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 500000; mi.hIcon = LoadIcon(GetModuleHandle(NULL),MAKEINTRESOURCE(IDI_CLIENTMIRANDA)); mi.pszService = "Help/AboutCommand"; mi.pszName = LPGEN("&About"); //AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 100000; mi.hIcon = ImageList_GetIcon(hCListImages,NewGroupIconidx,0); mi.pszService = MS_CLIST_GROUPCREATE; mi.pszName = LPGEN("&New Group"); hNewGroupMenuItem = (HGENMENU)AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 100001; mi.hIcon = NULL; mi.pszService = MS_CLIST_SETHIDEOFFLINE; mi.pszName = LPGEN("&Hide Offline Users"); gmp.lParam = 0;gmp.wParam = -1; hHideOfflineUsersMenuItem = (HGENMENU)AddGroupMenuItem((WPARAM)&gmp,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 100002; mi.hIcon = NULL; mi.pszService = "CLISTMENUSGroup/HideOfflineRootHelper"; mi.pszName = LPGEN("Hide &Offline Users out here"); hHideOfflineUsersOutHereMenuItem = (HGENMENU)AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 100003; mi.hIcon = NULL; mi.pszService = "CLISTMENUSGroup/HideGroupsHelper"; mi.pszName = LPGEN("Hide &Empty Groups"); hHideEmptyGroupsMenuItem = (HGENMENU)AddGroupMenuItem(0,(LPARAM)&mi); memset(&mi,0,sizeof(mi)); mi.cbSize = sizeof(mi); mi.position = 100004; mi.hIcon = NULL; mi.pszService = "CLISTMENUSGroup/UseGroupsHelper"; mi.pszName = LPGEN("Disable &Groups"); hDisableGroupsMenuItem = (HGENMENU)AddGroupMenuItem(0,(LPARAM)&mi); HookEvent(ME_SKIN2_ICONSCHANGED,OnIconLibIconChanged); } }
/***************************************************************************** * SIC_OverlayShortcutImage [internal] * * NOTES * Creates a new icon as a copy of the passed-in icon, overlayed with a * shortcut image. */ static HICON SIC_OverlayShortcutImage(HICON SourceIcon, BOOL large) { ICONINFO SourceIconInfo, ShortcutIconInfo, TargetIconInfo; HICON ShortcutIcon, TargetIcon; BITMAP SourceBitmapInfo, ShortcutBitmapInfo; HDC SourceDC = NULL, ShortcutDC = NULL, TargetDC = NULL, ScreenDC = NULL; HBITMAP OldSourceBitmap = NULL, OldShortcutBitmap = NULL, OldTargetBitmap = NULL; static int s_imgListIdx = -1; /* Get information about the source icon and shortcut overlay */ if (! GetIconInfo(SourceIcon, &SourceIconInfo) || 0 == GetObjectW(SourceIconInfo.hbmColor, sizeof(BITMAP), &SourceBitmapInfo)) { return NULL; } /* search for the shortcut icon only once */ if (s_imgListIdx == -1) s_imgListIdx = SIC_LoadOverlayIcon(- IDI_SHELL_SHORTCUT); /* FIXME should use icon index 29 instead of the resource id, but not all icons are present yet so we can't use icon indices */ if (s_imgListIdx != -1) { if (large) ShortcutIcon = ImageList_GetIcon(ShellBigIconList, s_imgListIdx, ILD_TRANSPARENT); else ShortcutIcon = ImageList_GetIcon(ShellSmallIconList, s_imgListIdx, ILD_TRANSPARENT); } else ShortcutIcon = NULL; if (NULL == ShortcutIcon || ! GetIconInfo(ShortcutIcon, &ShortcutIconInfo) || 0 == GetObjectW(ShortcutIconInfo.hbmColor, sizeof(BITMAP), &ShortcutBitmapInfo)) { return NULL; } TargetIconInfo = SourceIconInfo; TargetIconInfo.hbmMask = NULL; TargetIconInfo.hbmColor = NULL; /* Setup the source, shortcut and target masks */ SourceDC = CreateCompatibleDC(NULL); if (NULL == SourceDC) goto fail; OldSourceBitmap = SelectObject(SourceDC, SourceIconInfo.hbmMask); if (NULL == OldSourceBitmap) goto fail; ShortcutDC = CreateCompatibleDC(NULL); if (NULL == ShortcutDC) goto fail; OldShortcutBitmap = SelectObject(ShortcutDC, ShortcutIconInfo.hbmMask); if (NULL == OldShortcutBitmap) goto fail; TargetDC = CreateCompatibleDC(NULL); if (NULL == TargetDC) goto fail; TargetIconInfo.hbmMask = CreateCompatibleBitmap(TargetDC, SourceBitmapInfo.bmWidth, SourceBitmapInfo.bmHeight); if (NULL == TargetIconInfo.hbmMask) goto fail; ScreenDC = GetDC(NULL); if (NULL == ScreenDC) goto fail; TargetIconInfo.hbmColor = CreateCompatibleBitmap(ScreenDC, SourceBitmapInfo.bmWidth, SourceBitmapInfo.bmHeight); ReleaseDC(NULL, ScreenDC); if (NULL == TargetIconInfo.hbmColor) goto fail; OldTargetBitmap = SelectObject(TargetDC, TargetIconInfo.hbmMask); if (NULL == OldTargetBitmap) goto fail; /* Create the target mask by ANDing the source and shortcut masks */ if (! BitBlt(TargetDC, 0, 0, SourceBitmapInfo.bmWidth, SourceBitmapInfo.bmHeight, SourceDC, 0, 0, SRCCOPY) || ! BitBlt(TargetDC, 0, SourceBitmapInfo.bmHeight - ShortcutBitmapInfo.bmHeight, ShortcutBitmapInfo.bmWidth, ShortcutBitmapInfo.bmHeight, ShortcutDC, 0, 0, SRCAND)) { goto fail; } /* Setup the source and target xor bitmap */ if (NULL == SelectObject(SourceDC, SourceIconInfo.hbmColor) || NULL == SelectObject(TargetDC, TargetIconInfo.hbmColor)) { goto fail; } /* Copy the source xor bitmap to the target and clear out part of it by using the shortcut mask */ if (! BitBlt(TargetDC, 0, 0, SourceBitmapInfo.bmWidth, SourceBitmapInfo.bmHeight, SourceDC, 0, 0, SRCCOPY) || ! BitBlt(TargetDC, 0, SourceBitmapInfo.bmHeight - ShortcutBitmapInfo.bmHeight, ShortcutBitmapInfo.bmWidth, ShortcutBitmapInfo.bmHeight, ShortcutDC, 0, 0, SRCAND)) { goto fail; } if (NULL == SelectObject(ShortcutDC, ShortcutIconInfo.hbmColor)) goto fail; /* Now put in the shortcut xor mask */ if (! BitBlt(TargetDC, 0, SourceBitmapInfo.bmHeight - ShortcutBitmapInfo.bmHeight, ShortcutBitmapInfo.bmWidth, ShortcutBitmapInfo.bmHeight, ShortcutDC, 0, 0, SRCINVERT)) { goto fail; } /* Clean up, we're not goto'ing to 'fail' after this so we can be lazy and not set handles to NULL */ SelectObject(TargetDC, OldTargetBitmap); DeleteObject(TargetDC); SelectObject(ShortcutDC, OldShortcutBitmap); DeleteObject(ShortcutDC); SelectObject(SourceDC, OldSourceBitmap); DeleteObject(SourceDC); /* Create the icon using the bitmaps prepared earlier */ TargetIcon = CreateIconIndirect(&TargetIconInfo); /* CreateIconIndirect copies the bitmaps, so we can release our bitmaps now */ DeleteObject(TargetIconInfo.hbmColor); DeleteObject(TargetIconInfo.hbmMask); return TargetIcon; fail: /* Clean up scratch resources we created */ if (NULL != OldTargetBitmap) SelectObject(TargetDC, OldTargetBitmap); if (NULL != TargetIconInfo.hbmColor) DeleteObject(TargetIconInfo.hbmColor); if (NULL != TargetIconInfo.hbmMask) DeleteObject(TargetIconInfo.hbmMask); if (NULL != TargetDC) DeleteObject(TargetDC); if (NULL != OldShortcutBitmap) SelectObject(ShortcutDC, OldShortcutBitmap); if (NULL != ShortcutDC) DeleteObject(ShortcutDC); if (NULL != OldSourceBitmap) SelectObject(SourceDC, OldSourceBitmap); if (NULL != SourceDC) DeleteObject(SourceDC); return NULL; }
HICON fnGetIconFromStatusMode(MCONTACT hContact, const char *szProto, int status) { return ImageList_GetIcon(hCListImages, cli.pfnIconFromStatusMode(szProto, status, hContact), ILD_NORMAL); }
int Meta_ModifyMenu(WPARAM hMeta, LPARAM) { DBCachedContact *cc = currDb->m_cache->GetCachedContact(hMeta); if (cc == NULL) return 0; Menu_ShowItem(hMenuRoot, false); if (cc->IsMeta()) { // save the mouse pos in case they open a subcontact menu GetCursorPos(&menuMousePoint); // This is a MetaContact, show the edit, force default, and the delete menu, and hide the others Menu_ShowItem(hMenuEdit, true); Menu_ShowItem(hMenuAdd, false); Menu_ShowItem(hMenuConvert, false); Menu_ShowItem(hMenuDefault, false); Menu_ShowItem(hMenuDelete, false); Menu_ModifyItem(hMenuDelete, LPGENT("Remove from metacontact")); // show subcontact menu items CMString tszNick; for (int i = 0; i < MAX_CONTACTS; i++) { if (i >= cc->nSubs) { Menu_ShowItem(hMenuContact[i], false); continue; } MCONTACT hContact = Meta_GetContactHandle(cc, i); LPCTSTR ptszName; if (options.menu_contact_label == DNT_UID) { Meta_GetSubNick(hMeta, i, tszNick); ptszName = tszNick.GetBuffer(); } else ptszName = cli.pfnGetContactDisplayName(hContact, 0); int iconIndex = CallService(MS_CLIST_GETCONTACTICON, hContact, 0); HICON hIcon = ImageList_GetIcon((HIMAGELIST)CallService(MS_CLIST_GETICONSIMAGELIST, 0, 0), iconIndex, 0); Menu_ModifyItem(hMenuContact[i], ptszName, hIcon, 0); DestroyIcon(hIcon); Menu_ShowItem(hMenuRoot, true); } // show hide nudge menu item char serviceFunc[256]; mir_snprintf(serviceFunc, _countof(serviceFunc), "%s%s", GetContactProto(Meta_GetMostOnline(cc)), PS_SEND_NUDGE); CallService(MS_NUDGE_SHOWMENU, (WPARAM)META_PROTO, ServiceExists(serviceFunc)); return 0; } PROTOACCOUNT *pa = Proto_GetAccount(cc->szProto); if (!db_mc_isEnabled() || !pa || pa->bIsVirtual) { // groups disabled - all meta menu options hidden Menu_ShowItem(hMenuDefault, false); Menu_ShowItem(hMenuDelete, false); Menu_ShowItem(hMenuAdd, false); Menu_ShowItem(hMenuConvert, false); Menu_ShowItem(hMenuEdit, false); return 0; } // the contact is affected to a metacontact if (cc->IsSub()) { Menu_ShowItem(hMenuDefault, true); Menu_ModifyItem(hMenuDelete, LPGENT("Remove from metacontact")); Menu_ShowItem(hMenuDelete, true); Menu_ShowItem(hMenuAdd, false); Menu_ShowItem(hMenuConvert, false); Menu_ShowItem(hMenuEdit, false); } else { // The contact is neutral bool bHideChat = db_get_b(hMeta, cc->szProto, "ChatRoom", 0) == 0; Menu_ShowItem(hMenuAdd, bHideChat); Menu_ShowItem(hMenuConvert, bHideChat); Menu_ShowItem(hMenuEdit, false); Menu_ShowItem(hMenuDelete, false); Menu_ShowItem(hMenuDefault, false); } for (int i = 0; i < MAX_CONTACTS; i++) Menu_ShowItem(hMenuContact[i], false); return 0; }