/** * Responsible for drawing each list item. */ void ToggleListView::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct) { CListCtrl& ListCtrl=GetListCtrl(); int nItem = lpDrawItemStruct->itemID; // get item data LV_ITEM lvi; _TCHAR szBuff[MAX_PATH]; memset(&lvi, 0, sizeof(LV_ITEM)); lvi.mask = LVIF_TEXT; lvi.iItem = nItem; lvi.pszText = szBuff; lvi.cchTextMax = sizeof(szBuff); ListCtrl.GetItem(&lvi); RECT rDraw; CopyRect ( &rDraw, &lpDrawItemStruct->rcItem ); rDraw.right = rDraw.left + TOGGLELIST_ITEMHEIGHT; rDraw.top ++; rDraw.right ++; FrameRect ( lpDrawItemStruct->hDC, &rDraw, (HBRUSH)GetStockObject ( BLACK_BRUSH ) ); rDraw.right --; FillRect ( lpDrawItemStruct->hDC, &rDraw, GetSysColorBrush ( COLOR_3DFACE ) ); Draw3dRect ( lpDrawItemStruct->hDC, &rDraw, GetSysColorBrush ( COLOR_3DHILIGHT ), GetSysColorBrush ( COLOR_3DSHADOW ) ); InflateRect ( &rDraw, -3, -3 ); Draw3dRect ( lpDrawItemStruct->hDC, &rDraw, GetSysColorBrush ( COLOR_3DSHADOW ), GetSysColorBrush ( COLOR_3DHILIGHT ) ); switch(GetToggleState(lvi.iItem)) { case TOGGLE_STATE_DISABLED: if(disabledIcon) { DrawIconEx ( lpDrawItemStruct->hDC, rDraw.left, rDraw.top, disabledIcon, 16, 16,0, NULL, DI_NORMAL ); } break; case TOGGLE_STATE_ON: if(onIcon) { DrawIconEx ( lpDrawItemStruct->hDC, rDraw.left, rDraw.top, onIcon, 16, 16,0, NULL, DI_NORMAL ); } break; case TOGGLE_STATE_OFF: if(offIcon) { DrawIconEx ( lpDrawItemStruct->hDC, rDraw.left, rDraw.top, offIcon, 16, 16,0, NULL, DI_NORMAL ); } break; }; CopyRect ( &rDraw, &lpDrawItemStruct->rcItem ); rDraw.left += TOGGLELIST_ITEMHEIGHT; rDraw.left += 1; if ( lpDrawItemStruct->itemState & ODS_SELECTED ) { FillRect ( lpDrawItemStruct->hDC, &rDraw, GetSysColorBrush ( COLOR_HIGHLIGHT ) ); } else { FillRect ( lpDrawItemStruct->hDC, &rDraw, GetSysColorBrush ( COLOR_WINDOW ) ); } rDraw.left += TEXT_OFFSET; int colorIndex = ( (lpDrawItemStruct->itemState & ODS_SELECTED ) ? COLOR_HIGHLIGHTTEXT : COLOR_WINDOWTEXT ); SetTextColor ( lpDrawItemStruct->hDC, GetSysColor ( colorIndex ) ); DrawText ( lpDrawItemStruct->hDC, szBuff, strlen(szBuff), &rDraw, DT_LEFT|DT_VCENTER|DT_SINGLELINE ); }
void MainWnd_OnDrawItem(HWND hwnd, const DRAWITEMSTRUCT *lpDrawItem) { if (lpDrawItem->CtlType != ODT_LISTVIEW) return; HDC hDC = lpDrawItem->hDC; SetBkMode(hDC, TRANSPARENT); INT iColumn = 0, x, cx; RECT rcItem, rcSubItem, rcText; STRING Str; x = -GetScrollPos(g_hListView, SB_HORZ); rcItem = lpDrawItem->rcItem; if (lpDrawItem->itemState & ODS_SELECTED) { FillRect(hDC, &rcItem, (HBRUSH)(COLOR_HIGHLIGHT + 1)); SetTextColor(hDC, GetSysColor(COLOR_HIGHLIGHTTEXT)); } else { FillRect(hDC, &rcItem, (HBRUSH)(COLOR_WINDOW + 1)); SetTextColor(hDC, GetSysColor(COLOR_WINDOWTEXT)); } cx = ListView_GetColumnWidth(g_hListView, iColumn); rcSubItem = rcItem; rcSubItem.left = x; rcSubItem.right = x + cx; WCHAR sz[MAX_STRING]; rcText = rcSubItem; InflateRect(&rcText, -1, -1); Str = g_Items[lpDrawItem->itemID].m_Name; BYTE CharSet1 = g_Items[lpDrawItem->itemID].m_CharSet1; if (CharSet1 != DEFAULT_CHARSET) wsprintfW(sz, L"%s,%u", Str.c_str(), CharSet1); else wsprintfW(sz, L"%s", Str.c_str()); DrawTextW(hDC, sz, lstrlenW(sz), &rcText, DT_SINGLELINE | DT_LEFT | DT_VCENTER | DT_END_ELLIPSIS | DT_NOPREFIX); x += cx; ++iColumn; cx = ListView_GetColumnWidth(g_hListView, iColumn); rcSubItem = rcItem; rcSubItem.left = x; rcSubItem.right = x + cx; rcText = rcSubItem; InflateRect(&rcText, -1, -1); Str = g_Items[lpDrawItem->itemID].m_Substitute; BYTE CharSet2 = g_Items[lpDrawItem->itemID].m_CharSet2; if (CharSet2 != DEFAULT_CHARSET) wsprintfW(sz, L"%s,%u", Str.c_str(), CharSet2); else wsprintfW(sz, L"%s", Str.c_str()); DrawTextW(hDC, sz, lstrlenW(sz), &rcText, DT_SINGLELINE | DT_LEFT | DT_VCENTER | DT_END_ELLIPSIS | DT_NOPREFIX); }
/* ================ ColorButton_DrawItem Draws the actual color button as as reponse to a WM_DRAWITEM message ================ */ void ColorButton_DrawItem ( HWND hWnd, LPDRAWITEMSTRUCT dis ) { assert ( dis ); HDC hDC = dis->hDC; UINT state = dis->itemState; RECT rDraw = dis->rcItem; RECT rArrow; // Draw outter edge UINT uFrameState = DFCS_BUTTONPUSH|DFCS_ADJUSTRECT; if (state & ODS_SELECTED) { uFrameState |= DFCS_PUSHED; } if (state & ODS_DISABLED) { uFrameState |= DFCS_INACTIVE; } DrawFrameControl ( hDC, &rDraw, DFC_BUTTON, uFrameState ); // Draw Focus if (state & ODS_SELECTED) { OffsetRect(&rDraw, 1,1); } if (state & ODS_FOCUS) { RECT rFocus = {rDraw.left, rDraw.top, rDraw.right - 1, rDraw.bottom}; DrawFocusRect ( hDC, &rFocus ); } InflateRect ( &rDraw, -GetSystemMetrics(SM_CXEDGE), -GetSystemMetrics(SM_CYEDGE) ); // Draw the arrow rArrow.left = rDraw.right - ARROW_SIZE_CX - GetSystemMetrics(SM_CXEDGE) /2; rArrow.right = rArrow.left + ARROW_SIZE_CX; rArrow.top = (rDraw.bottom + rDraw.top)/2 - ARROW_SIZE_CY / 2; rArrow.bottom = (rDraw.bottom + rDraw.top)/2 + ARROW_SIZE_CY / 2; ColorButton_DrawArrow ( hDC, &rArrow, (state & ODS_DISABLED) ? ::GetSysColor(COLOR_GRAYTEXT) : RGB(0,0,0) ); rDraw.right = rArrow.left - GetSystemMetrics(SM_CXEDGE)/2; // Draw separator DrawEdge ( hDC, &rDraw, EDGE_ETCHED, BF_RIGHT); rDraw.right -= (GetSystemMetrics(SM_CXEDGE) * 2) + 1 ; // Draw Color if ((state & ODS_DISABLED) == 0) { HBRUSH color = CreateSolidBrush ( (COLORREF)GetWindowLong ( hWnd, GWL_USERDATA ) ); FillRect ( hDC, &rDraw, color ); FrameRect ( hDC, &rDraw, (HBRUSH)::GetStockObject(BLACK_BRUSH)); DeleteObject( color ); } }
static VOID MonSelPaintMonitor(IN OUT PMONITORSELWND infoPtr, IN HDC hDC, IN DWORD Index, IN OUT PRECT prc, IN COLORREF crDefFontColor, IN BOOL bHideNumber) { HFONT hFont, hPrevFont; COLORREF crPrevText; if ((INT)Index == infoPtr->SelectedMonitor) { FillRect(hDC, prc, (HBRUSH)(COLOR_HIGHLIGHT + 1)); if (infoPtr->HasFocus && !(infoPtr->UIState & UISF_HIDEFOCUS)) { /* NOTE: We need to switch the text color to the default, because DrawFocusRect draws a solid line if the text is white! */ crPrevText = SetTextColor(hDC, crDefFontColor); DrawFocusRect(hDC, prc); SetTextColor(hDC, crPrevText); } } InflateRect(prc, -infoPtr->SelectionFrame.cx, -infoPtr->SelectionFrame.cy); Rectangle(hDC, prc->left, prc->top, prc->right, prc->bottom); InflateRect(prc, -1, -1); if (!bHideNumber) { hFont = MonSelGetMonitorFont(infoPtr, hDC, Index); if (hFont != NULL) { hPrevFont = SelectObject(hDC, hFont); DrawText(hDC, infoPtr->Monitors[Index].szCaption, -1, prc, DT_VCENTER | DT_CENTER | DT_NOPREFIX | DT_SINGLELINE); SelectObject(hDC, hPrevFont); } } if (infoPtr->MonitorInfo[Index].Flags & MSL_MIF_DISABLED) { InflateRect(prc, 1, 1); MonSelDrawDisabledRect(infoPtr, hDC, prc); } }
LRESULT CALLBACK WndProc (HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { HDC hDC; /* Структура PAINTSTRUCT содержит информации для приложения. Эта информация может быть использована для окраски клиентской области окна, которым владеет приложение. HDC hdc; BOOL fErase; Определяет, должен ли фон быть стерт. Значение этого параметра должно быть не равно нулю, если приложение должно стирать фон. RECT rcPaint; Задает стурктуру RECT, которая определяет верхний левый и нижний правый углы прямоугольника, в котором требуется прорисовка. BOOL fRestore; BOOL fIncUpdate; BYTE rgbReserved[32]; */ PAINTSTRUCT ps; TEXTMETRIC tm; static COLORREF textColor; RECT rcClient; int cxClient=0, cyClient=0; static int xInc, yInc; //Внутри этой структуры координаты углов. //Верхний левый угол определяется двумя координатами left и top. //Нижний правый соответственно определяется вдумя оставшимися координатами right и bottom. RECT rect; int dX, dY; int ws, hs, wd, hd, wd_s, hd_s; int mouseX=0, mouseY=0; static BOOL isFileLoaded; static BOOL isFileLoaded_help; unsigned int DRAW_N=2; // Переменные для стандартного диалога "Open" static OPENFILENAME ofn; static char szFile[MAX_PATH]; // Переменные для стандартного диалога "Color" static CHOOSECOLOR cc; // common dialog box structure static COLORREF acrCustClr[16]; // array of custom colors // Переменные для стандартного диалога "Font" static CHOOSEFONT chf; static HFONT hFont; static LOGFONT lf; //---------------------------------------------------------------------------------------------------------------- //---------------------------------------------------------------------------------------------------------------- switch (uMsg) { case WM_CREATE: page=1; success=0; name_change=0; // Инициализация структуры ofn ofn.lStructSize = sizeof(OPENFILENAME); ofn.hwndOwner = hWnd; ofn.lpstrFile = szFile; ofn.nMaxFile = sizeof(szFile); ofn.lpstrFilter = TEXT("Text Files(*.txt)\0*.txt\0"); //открывает только .txt // Инициализация структуры cc cc.lStructSize = sizeof(CHOOSECOLOR); cc.hwndOwner = hWnd; cc.lpCustColors = (LPDWORD) acrCustClr; cc.Flags = CC_FULLOPEN | CC_RGBINIT; // Инициализация структуры chf chf.lStructSize = sizeof(CHOOSEFONT); chf.hwndOwner = hWnd; chf.lpLogFont = &lf; chf.Flags = CF_SCREENFONTS | CF_INITTOLOGFONTSTRUCT; chf.nFontType = SIMULATED_FONTTYPE; hDC= GetDC (hWnd); GetTextMetrics(hDC, &tm); doc.Initialize(&tm); ReleaseDC(hWnd, hDC); isFileLoaded = menu.LoadFromFile (MENU); if (!isFileLoaded) { MessageBox (hWnd, "File " MENU " don't loaded ", "Error", MB_OK); break; } isFileLoaded_help = help.LoadFromFile (HELP); if (!isFileLoaded_help) { MessageBox (hWnd, "File " HELP " don't loaded ", "Error", MB_OK); break; } // gдогнать размеры окна программы под размер растра bmp // Для получения области клиента GetClientRect (hWnd, &rect); dX = menu.GetWidth () - rect.right; dY = menu.GetHeight() - rect.bottom; // Для получение прямоугольника приложения GetWindowRect (hWnd, &rect); // Модифициpует высоту и шиpину Rect. Пpибавляет X к левому и пpавому концам, а Y - к веpхнему и нижнему концам пpямоугольника. InflateRect (&rect, dX/2, dY/2); // Посылает окну сообщение wm_Size. Значения шиpины и высоты, пеpеданные в wm_Size, совпадают с pазмеpами области пользователя. MoveWindow (hWnd, rect.left, rect.top, rect.right-rect.left, rect.bottom-rect.top, TRUE); // Освобождает общий или оконный (не влияющий на класс или локальность) контекст устpойства, делая его доступным для дpугих пpикладных задач. ReleaseDC (hWnd, hDC); break; //---------------------------------------------------------------------------------------------------------------- //---------------------------------------------------------------------------------------------------------------- case WM_SIZE: hDC = GetDC(hWnd); cxClient = LOWORD(lParam); cyClient = HIWORD(lParam); if (cxClient > 0) doc.ScrollSettings(hWnd, cxClient, cyClient); ReleaseDC(hWnd, hDC); break; //---------------------------------------------------------------------------------------------------------------- //для прокрутки //---------------------------------------------------------------------------------------------------------------- case WM_VSCROLL: switch(LOWORD(wParam)) { case SB_LINEUP: yInc = -1; break; case SB_LINEDOWN: yInc = 1; break; case SB_PAGEUP: yInc = -(int)doc.vsi.nPage; break; case SB_PAGEDOWN: yInc = (int)doc.vsi.nPage; break; case SB_THUMBTRACK: yInc = HIWORD(wParam) - doc.vsi.nPos; break; default: yInc = 0; } doc.UpdateVscroll(hWnd, yInc); break; case WM_HSCROLL: switch(LOWORD(wParam)) { case SB_LINELEFT: xInc = -1; break; case SB_LINERIGHT: xInc = 1; break; case SB_PAGELEFT: xInc = -0.8 * (int)doc.hsi.nPage; break; case SB_PAGERIGHT: xInc = 0.8 * (int)doc.hsi.nPage; break; case SB_THUMBTRACK: xInc = HIWORD(wParam) - doc.hsi.nPos; break; default: xInc = 0; } doc.UpdateHscroll(hWnd, xInc); break; //---------------------------------------------------------------------------------------------------------------- //---------------------------------------------------------------------------------------------------------------- case WM_COMMAND: { switch (LOWORD(wParam)) { //-------------------------------------------------------------------- case IDM_OPEN: page=1; strcpy(szFile, ""); success = GetOpenFileName(&ofn); if (success) { MessageBox(hWnd, ofn.lpstrFile, "OK. File was loaded.", MB_OK); name = ofn.lpstrFile; name+='\n'; name=path_reform(name); --att; name_change=1; } else MessageBox(hWnd, ESC_OF, "ERROR! Failure or file wasn't founded ", MB_ICONWARNING); InvalidateRect (hWnd, NULL, 1); SendMessage (hWnd,WM_PAINT, wParam, lParam); break; //----------------------------------------------------------------- case ID_HELP_ABOUT: page=3; InvalidateRect (hWnd, NULL, 1); SendMessage (hWnd,WM_PAINT, wParam, lParam); break; //----------------------------------------------------------------- case IDM_EXIT: SendMessage(hWnd, WM_DESTROY, 0, 0); break; //----------------------------------------------------------------- case ID_RUN_RUSSIAN: if (!success) {MessageBox(hWnd, ESC_OF, "ERROR! Firstly, choose the file. ", MB_ICONWARNING);break;} language=1; analysis_of_file (hWnd); out_statistic (); if (att<0) {MessageBox(hWnd, ESC_OF, "No attempts. ", MB_ICONWARNING); SendMessage(hWnd, WM_DESTROY, 0, 0); break;} if (name_change==1){ tempr[att] = new char[statistic_file_name.size()]; strcpy( tempr[att], statistic_file_name.c_str() );} if (!doc.Open(tempr[att])) return 0; page=2; InvalidateRect (hWnd, NULL, 1); SendMessage (hWnd,WM_PAINT, wParam, lParam); name_change=0; break; //-------------------------------------------------------------- case ID_RUN_ENGLISH: if (!success) {MessageBox(hWnd, ESC_OF, "ERROR! Firstly, choose the file. ", MB_ICONWARNING); break;} language=2; analysis_of_file (hWnd); out_statistic (); if (att<0) {MessageBox(hWnd, ESC_OF, "No attempts. ", MB_ICONWARNING); SendMessage(hWnd, WM_DESTROY, 0, 0); break;} if (name_change==1){ tempr[att] = new char[statistic_file_name.size()]; strcpy( tempr[att], statistic_file_name.c_str() );} if (!doc.Open(tempr[att])) return 0; page=2; InvalidateRect (hWnd, NULL, 1); SendMessage (hWnd,WM_PAINT, wParam, lParam); name_change=0; break; //------------------------------------------------------------- case ID_RUN_RUS: if (!success) {MessageBox(hWnd, ESC_OF, "No attempts. ", MB_ICONWARNING); SendMessage(hWnd, WM_DESTROY, 0, 0); break;} language=3; analysis_of_file (hWnd); out_statistic (); if (att<0) {SendMessage(hWnd, WM_DESTROY, 0, 0); break;} if (name_change==1){ tempr[att] = new char[statistic_file_name.size()]; strcpy( tempr[att], statistic_file_name.c_str() );} if (!doc.Open(tempr[att])) return 0; page=2; InvalidateRect (hWnd, NULL, 1); SendMessage (hWnd,WM_PAINT, wParam, lParam); name_change=0; break; //------------------------------------------------------------ case IDM_BKGR_COLOR: if (ChooseColor(&cc)) SetClassLong(hWnd, GCL_HBRBACKGROUND, (LONG)CreateSolidBrush(cc.rgbResult)); break; //------------------------------------------------------------ case IDM_TEXT_COLOR: if (ChooseColor(&cc)) textColor = cc.rgbResult; break; //------------------------------------------------------------ case IDM_CHOOSE_FONT: if(ChooseFont(&chf)) hFont = CreateFontIndirect(chf.lpLogFont); break; //------------------------------------------------------------ default : InvalidateRect(hWnd, NULL, TRUE); break; } } //---------------------------------------------------------------------------------------------------------------- //---------------------------------------------------------------------------------------------------------------- case WM_PAINT: hDC = BeginPaint (hWnd, &ps); wd = ws = menu.GetWidth (); hd = hs = menu.GetHeight (); switch (page) { case 1: menu.Draw (hDC, 0, 0, wd, hd, 0, 0, ws, hs, SRCCOPY); statistic_file_name="out.txt"; break; case 2: menu.Draw (hDC, 0, 0, wd, hd, 0, 0, ws, hs, SRCCOPY); SetBkMode(hDC, TRANSPARENT); SetTextColor(hDC, textColor); if (hFont) DeleteObject(SelectObject(hDC, hFont)); GetClientRect(hWnd, &rect); doc.PutText(hWnd, hDC); statistic_file_name="out.txt"; break; case 3: help.Draw (hDC, 0, 0, wd, hd, 0, 0, ws, hs, SRCCOPY); statistic_file_name="out.txt"; break; default: menu.Draw (hDC, 0, 0, wd, hd, 0, 0, ws, hs, SRCCOPY); SetBkMode(hDC, TRANSPARENT); GetClientRect(hWnd, &rect); break; } EndPaint (hWnd, &ps); break; //---------------------------------------------------------------------------------------------------------------- //---------------------------------------------------------------------------------------------------------------- case WM_DESTROY: dictionary.clear(); PostQuitMessage (0); break; default: return DefWindowProc (hWnd, uMsg, wParam, lParam); } return 0; }
// UpDownWndProc: // LRESULT CALLBACK UpDownWndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { RECT rc; int i; PUDSTATE np = (PUDSTATE)GetWindowInt(hwnd, 0); if (np) { if ((uMsg >= WM_MOUSEFIRST) && (uMsg <= WM_MOUSELAST) && (np->ci.style & UDS_HOTTRACK) && !np->fTrackSet) { TRACKMOUSEEVENT tme; np->fTrackSet = TRUE; tme.cbSize = sizeof(tme); tme.hwndTrack = np->ci.hwnd; tme.dwFlags = TME_LEAVE; TrackMouseEvent(&tme); } } switch (uMsg) { case WM_MOUSEMOVE: UD_OnMouseMove(np, lParam); break; case WM_MOUSELEAVE: np->fTrackSet = FALSE; UD_Invalidate(np, np->uHot, FALSE); np->uHot = UD_HITNOWHERE; break; case WM_LBUTTONDOWN: { // Don't set a timer if on the middle border BOOL bTimeIt = TRUE; if (np->hwndBuddy && !IsWindowEnabled(np->hwndBuddy)) break; SetCapture(hwnd); getint(np); switch (np->uClass) { case CLASS_EDIT: case CLASS_LISTBOX: SetFocus(np->hwndBuddy); break; } switch(UD_HitTest(np, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam))) { case UD_HITDOWN: np->bDown = TRUE; squish(np, FALSE, TRUE); break; case UD_HITUP: np->bDown = FALSE; squish(np, TRUE, FALSE); break; case UD_HITNOWHERE: bTimeIt = FALSE; break; } if (bTimeIt) { SetTimer(hwnd, 1, GetProfileInt(TEXT("windows"), TEXT("CursorBlinkRate"), 530), NULL); bump(np); } break; } case WM_TIMER: { POINT pt; if (GetCapture() != hwnd) { goto EndScroll; } SetTimer(hwnd, 1, 100, NULL); GetWindowRect(hwnd, &rc); if (np->ci.style & UDS_HORZ) { i = (rc.left + rc.right) / 2; if (np->bDown) { rc.right = i; } else { rc.left = i; } } else { i = (rc.top + rc.bottom) / 2; if (np->bDown) { rc.top = i; } else { rc.bottom = i; } } InflateRect(&rc, (g_cxFrame+1)/2, (g_cyFrame+1)/2); GetCursorPos(&pt); if (PtInRect(&rc, pt)) { squish(np, !np->bDown, np->bDown); bump(np); } else { squish(np, FALSE, FALSE); } break; } case WM_LBUTTONUP: if (np->hwndBuddy && !IsWindowEnabled(np->hwndBuddy)) break; if (GetCapture() == hwnd) { EndScroll: squish(np, FALSE, FALSE); ReleaseCapture(); KillTimer(hwnd, 1); if (np->uClass == CLASS_EDIT) Edit_SetSel(np->hwndBuddy, 0, -1); if (np->ci.style & UDS_HORZ) FORWARD_WM_HSCROLL(np->ci.hwndParent, np->ci.hwnd, SB_ENDSCROLL, np->nPos, SendMessage); else FORWARD_WM_VSCROLL(np->ci.hwndParent, np->ci.hwnd, SB_ENDSCROLL, np->nPos, SendMessage); } break; case WM_ENABLE: InvalidateRect(hwnd, NULL, TRUE); break; case WM_WININICHANGE: if (np && (!wParam || (wParam == SPI_SETNONCLIENTMETRICS) || (wParam == SPI_SETICONTITLELOGFONT))) { InitGlobalMetrics(wParam); unachor(np); anchor(np); } break; case WM_PRINTCLIENT: case WM_PAINT: PaintUpDownControl(np, (HDC)wParam); break; case UDM_SETRANGE: np->nUpper = GET_X_LPARAM(lParam); np->nLower = GET_Y_LPARAM(lParam); nudge(np); break; case UDM_GETRANGE: return MAKELONG(np->nUpper, np->nLower); case UDM_SETBASE: // wParam: new base // lParam: not used // return: 0 if invalid base is specified, // previous base otherwise return (LRESULT)setbase(np, (UINT)wParam); case UDM_GETBASE: return np->nBase; case UDM_SETPOS: { int iNewPos = GET_X_LPARAM(lParam); if (compare(np, np->nLower, np->nUpper, DONTCARE) < 0) { if (compare(np, iNewPos, np->nUpper, DONTCARE) > 0) { iNewPos = np->nUpper; } if (compare(np, iNewPos, np->nLower, DONTCARE) < 0) { iNewPos = np->nLower; } } else { if (compare(np, iNewPos, np->nUpper, DONTCARE) < 0) { iNewPos = np->nUpper; } if (compare(np, iNewPos, np->nLower, DONTCARE) > 0) { iNewPos = np->nLower; } } i = np->nPos; np->nPos = iNewPos; setint(np); #ifdef ACTIVE_ACCESSIBILITY MyNotifyWinEvent(EVENT_OBJECT_VALUECHANGE, np->ci.hwnd, OBJID_CLIENT, 0); #endif return (LRESULT)i; } case UDM_GETPOS: return getint(np); case UDM_SETBUDDY: return setbuddy(np, (HWND)wParam); case UDM_GETBUDDY: return (LRESULT)(int)np->hwndBuddy; case UDM_SETACCEL: if (wParam == 0) return(FALSE); if (wParam >= NUM_UDACCELS) { HANDLE npPrev = (HANDLE)np; np = (PUDSTATE)LocalReAlloc((HLOCAL)np, sizeof(UDSTATE)+(wParam-NUM_UDACCELS)*sizeof(UDACCEL), LMEM_MOVEABLE); if (!np) { return(FALSE); } else { SetWindowInt(hwnd, 0, (int)np); if ((np->ci.style & UDS_ARROWKEYS) && np->hwndBuddy) { SetWindowSubclass(np->hwndBuddy, ArrowKeyProc, 0, (DWORD)np); } } } np->nAccel = wParam; for (i=0; i<(int)wParam; ++i) { np->udAccel[i] = ((LPUDACCEL)lParam)[i]; } return(TRUE); case UDM_GETACCEL: if (wParam > np->nAccel) { wParam = np->nAccel; } for (i=0; i<(int)wParam; ++i) { ((LPUDACCEL)lParam)[i] = np->udAccel[i]; } return(np->nAccel); case WM_NOTIFYFORMAT: return CIHandleNotifyFormat(&np->ci, lParam); case WM_CREATE: // Allocate the instance data space. np = (PUDSTATE)LocalAlloc(LPTR, sizeof(UDSTATE)); if (!np) return -1; SetWindowInt(hwnd, 0, (int)np); #define lpCreate ((CREATESTRUCT FAR *)lParam) CIInitialize(&np->ci, hwnd, lpCreate); // np->fUp = // np->fDown = // np->fUnsigned = // np->fSharedBorder = // np->fSunkenBorder = // FALSE; if (lpCreate->dwExStyle & WS_EX_CLIENTEDGE) np->fSunkenBorder = TRUE; np->nBase = BASE_DECIMAL; np->nUpper = 0; np->nLower = 100; np->nPos = 0; np->hwndBuddy = NULL; np->uClass = CLASS_UNKNOWN; np->nAccel = NUM_UDACCELS; np->udAccel[0].nSec = 0; np->udAccel[0].nInc = 1; np->udAccel[1].nSec = 2; np->udAccel[1].nInc = 5; np->udAccel[2].nSec = 5; np->udAccel[2].nInc = 20; /* This does the pickbuddy and anchor */ setbuddy(np, NULL); setint(np); break; case WM_DESTROY: if (np) { if (np->hwndBuddy) { // Make sure that our buddy is unsubclassed. DebugMsg(DM_ERROR, TEXT("UpDown Destroyed while buddy subclassed")); np->fUpDownDestroyed = TRUE; } else LocalFree((HLOCAL)np); SetWindowInt(hwnd, 0, 0); } break; default: return DefWindowProc(hwnd, uMsg, wParam, lParam); } return 0L; }
void WndSymbolButton::on_paint(Canvas &canvas) { /* background and selector */ canvas.clear(background_brush); // Get button RECT and shrink it to make room for the selector/focus RECT rc = get_client_rect(); // Draw button to the background canvas.draw_button(rc, is_down()); // Draw focus rectangle if (has_focus()) { RECT focus_rc = rc; InflateRect(&focus_rc, -3, -3); canvas.draw_focus(focus_rc); } // If button has text on it tstring caption = get_text(); if (caption.empty()) return; // If button is pressed, offset the text for 3D effect if (is_down()) OffsetRect(&rc, 1, 1); canvas.null_pen(); canvas.black_brush(); const char ch = (char)caption[0]; // Draw arrow symbols instead of < and > if (ch == '<' || ch == '>') { int size = min(rc.right - rc.left, rc.bottom - rc.top) / 5; static RasterPoint Arrow[4]; Arrow[0].x = (rc.left + rc.right) / 2 + (ch == '<' ? size : -size); Arrow[0].y = (rc.top + rc.bottom) / 2 + size; Arrow[1].x = (rc.left + rc.right) / 2 + (ch == '<' ? -size : size); Arrow[1].y = (rc.top + rc.bottom) / 2; Arrow[2].x = (rc.left + rc.right) / 2 + (ch == '<' ? size : -size); Arrow[2].y = (rc.top + rc.bottom) / 2 - size; Arrow[3].x = Arrow[0].x; Arrow[3].y = Arrow[0].y; canvas.polygon(Arrow, 4); } // Draw arrow symbols instead of v and ^ if (ch == '^' || ch == 'v') { int size = min(rc.right - rc.left, rc.bottom - rc.top) / 5; RasterPoint Arrow[3]; Arrow[0].x = (rc.left + rc.right) / 2 + size; Arrow[0].y = (rc.top + rc.bottom) / 2 + (ch == '^' ? size : -size); Arrow[1].x = (rc.left + rc.right) / 2; Arrow[1].y = (rc.top + rc.bottom) / 2 + (ch == '^' ? -size : size); Arrow[2].x = (rc.left + rc.right) / 2 - size; Arrow[2].y = (rc.top + rc.bottom) / 2 + (ch == '^' ? size : -size); canvas.polygon(Arrow, 3); } // Draw symbols instead of + and - if (ch == '+' || ch == '-') { int size = min(rc.right - rc.left, rc.bottom - rc.top) / 5; canvas.rectangle((rc.left + rc.right) / 2 - size, (rc.top + rc.bottom) / 2 - size / 3, (rc.left + rc.right) / 2 + size, (rc.top + rc.bottom) / 2 + size / 3); if (ch == '+') canvas.rectangle((rc.left + rc.right) / 2 - size / 3, (rc.top + rc.bottom) / 2 - size, (rc.left + rc.right) / 2 + size / 3, (rc.top + rc.bottom) / 2 + size); } // Draw Fly bitmap if (caption == _T("Fly")) { Bitmap launcher1_bitmap(IDB_LAUNCHER1); if (is_down()) canvas.stretch(launcher1_bitmap); else { canvas.clear_white(); canvas.stretch_transparent(launcher1_bitmap, Color::BLUE); } } // Draw Simulator bitmap if (caption == _T("Simulator")) { Bitmap launcher2_bitmap(IDB_LAUNCHER2); if (is_down()) canvas.stretch(launcher2_bitmap); else { canvas.clear_white(); canvas.stretch_transparent(launcher2_bitmap, Color::BLUE); } } }
void MemMgr_GetWindowSizes (WINDOWSIZES *pSizes) { RECT rClient; GetClientRect (l.hManager, &rClient); InflateRect (&rClient, 0-cBORDER, 0-cBORDER); pSizes->rLabelAverage.right = rClient.right -cxBETWEEN*2; pSizes->rLabelAverage.top = rClient.top +8 +cyBETWEEN; pSizes->rLabelAverage.left = pSizes->rLabelAverage.right -cxVALUES; pSizes->rLabelAverage.bottom = pSizes->rLabelAverage.top +cyLABELS; pSizes->rLabelSize = pSizes->rLabelAverage; pSizes->rLabelSize.left -= cxBETWEEN + cxVALUES; pSizes->rLabelSize.right -= cxBETWEEN + cxVALUES; pSizes->rLabelCount = pSizes->rLabelSize; pSizes->rLabelCount.left -= cxBETWEEN + cxVALUES; pSizes->rLabelCount.right -= cxBETWEEN + cxVALUES; pSizes->rLabelCpp.left = rClient.left +cxBETWEEN; pSizes->rLabelCpp.top = pSizes->rLabelCount.bottom +cyBETWEEN; pSizes->rLabelCpp.right = pSizes->rLabelCpp.left +cxLABELS; pSizes->rLabelCpp.bottom = pSizes->rLabelCpp.top +cyLABELS; pSizes->rLabelOther = pSizes->rLabelCpp; pSizes->rLabelOther.top += cyBETWEEN + cyLABELS; pSizes->rLabelOther.bottom += cyBETWEEN + cyLABELS; pSizes->rLabelTotal = pSizes->rLabelOther; pSizes->rLabelTotal.top += cyBETWEEN + cyLABELS; pSizes->rLabelTotal.bottom += cyBETWEEN + cyLABELS; pSizes->rLabelTared = pSizes->rLabelTotal; pSizes->rLabelTared.top += cyBETWEEN + cyLABELS; pSizes->rLabelTared.bottom += cyBETWEEN + cyLABELS; pSizes->rBoxAlloc = rClient; pSizes->rBoxAlloc.bottom = pSizes->rLabelTared.bottom +cyBETWEEN; MIX (&pSizes->rValueCppCount, &pSizes->rLabelCpp, &pSizes->rLabelCount); MIX (&pSizes->rValueOtherCount, &pSizes->rLabelOther, &pSizes->rLabelCount); MIX (&pSizes->rValueTaredCount, &pSizes->rLabelTared, &pSizes->rLabelCount); MIX (&pSizes->rValueTotalCount, &pSizes->rLabelTotal, &pSizes->rLabelCount); MIX (&pSizes->rValueCppSize, &pSizes->rLabelCpp, &pSizes->rLabelSize); MIX (&pSizes->rValueOtherSize, &pSizes->rLabelOther, &pSizes->rLabelSize); MIX (&pSizes->rValueTaredSize, &pSizes->rLabelTared, &pSizes->rLabelSize); MIX (&pSizes->rValueTotalSize, &pSizes->rLabelTotal, &pSizes->rLabelSize); MIX (&pSizes->rValueCppAverage, &pSizes->rLabelCpp, &pSizes->rLabelAverage); MIX (&pSizes->rValueOtherAverage, &pSizes->rLabelOther, &pSizes->rLabelAverage); MIX (&pSizes->rValueTaredAverage, &pSizes->rLabelTared, &pSizes->rLabelAverage); MIX (&pSizes->rValueTotalAverage, &pSizes->rLabelTotal, &pSizes->rLabelAverage); pSizes->rBoxDetails = rClient; pSizes->rBoxDetails.top = pSizes->rBoxAlloc.bottom +cyBETWEEN; pSizes->rBoxDetails.bottom -= cyBUTTONS +cyBETWEEN; pSizes->rList = pSizes->rBoxDetails; pSizes->rList.top += 8; InflateRect (&pSizes->rList, 0-cBORDER, 0-cBORDER); pSizes->rClose = rClient; pSizes->rClose.top = pSizes->rClose.bottom - cyBUTTONS; pSizes->rClose.left = pSizes->rClose.right - cxBUTTONS; pSizes->rReset = pSizes->rClose; pSizes->rReset.right = pSizes->rClose.left - cxBETWEEN; pSizes->rReset.left = pSizes->rReset.right - cxBUTTONS; pSizes->rTare = pSizes->rClose; pSizes->rTare.right = pSizes->rReset.left - cxBETWEEN; pSizes->rTare.left = pSizes->rTare.right - cxBUTTONS; pSizes->rLabel = pSizes->rTare; pSizes->rLabel.right = pSizes->rTare.left - cxBETWEEN; pSizes->rLabel.left = pSizes->rLabel.right - cxBUTTONS; pSizes->rHide = pSizes->rLabel; pSizes->rHide.right = pSizes->rLabel.left - cxBETWEEN; pSizes->rHide.left = pSizes->rHide.right - cxBUTTONS; }
void VDPositionControlW32::OnPaint() { PAINTSTRUCT ps; HDC hdc = BeginPaint(mhwnd, &ps); if (!hdc) // hrm... this is bad return; HGDIOBJ hOldFont = SelectObject(hdc, mFrameNumberFont); SetBkMode(hdc, TRANSPARENT); SetTextColor(hdc, GetSysColor(COLOR_WINDOWTEXT)); SetTextAlign(hdc, TA_TOP | TA_CENTER); char buf[64]; RECT rClient; VDVERIFY(GetClientRect(mhwnd, &rClient)); int trackRight = mTrack.right; HGDIOBJ hOldPen = SelectObject(hdc, GetStockObject(BLACK_PEN)); // Determine digit spacing. int labelDigits = mRangeEnd > 0 ? (int)floor(log10((double)mRangeEnd)) + 1 : 1; int labelWidth = (labelDigits + 1) * mFrameNumberWidth; // Add 1 digit for nice padding. sint64 framesPerLabel = 1; if (mRangeEnd > mRangeStart) { while(framesPerLabel * mPixelsPerFrame < labelWidth) { sint64 fpl2 = framesPerLabel + framesPerLabel; if (fpl2 * mPixelsPerFrame >= labelWidth) { framesPerLabel = fpl2; break; } sint64 fpl5 = framesPerLabel * 5; if (fpl5 * mPixelsPerFrame >= labelWidth) { framesPerLabel = fpl5; break; } framesPerLabel *= 10; } } sint64 frame = mRangeStart; bool bDrawLabels = ps.rcPaint.bottom >= mTrackArea.bottom; while(frame < mRangeEnd) { int x = FrameToPixel(frame); const RECT rTick = { x, mTickArea.top, x+1, mTickArea.bottom }; FillRect(hdc, &rTick, mBrushes[kBrushTick]); if (x > trackRight - labelWidth) break; // don't allow labels to encroach last label if (bDrawLabels) { sprintf(buf, "%I64d", frame); TextOut(hdc, x, mTrackArea.bottom, buf, strlen(buf)); } frame += framesPerLabel; } const RECT rLastTick = { mTrack.right, mTrack.bottom, mTrack.right+1, mTrackArea.bottom }; FillRect(hdc, &rLastTick, mBrushes[kBrushTick]); if (bDrawLabels) { sprintf(buf, "%I64d", mRangeEnd); TextOut(hdc, trackRight, mTrackArea.bottom, buf, strlen(buf)); } // Fill the track. We draw the track borders later so they're always on top. FillRect(hdc, &mTrack, mBrushes[kBrushTrack]); // Draw selection and ticks. if (mSelectionEnd >= mSelectionStart) { int selx1 = FrameToPixel(mSelectionStart); int selx2 = FrameToPixel(mSelectionEnd); RECT rSel={selx1, mTrack.top, selx2, mTrack.bottom}; if (rSel.right == rSel.left) ++rSel.right; FillRect(hdc, &rSel, mBrushes[kBrushSelection]); if (HPEN hNullPen = CreatePen(PS_NULL, 0, 0)) { if (HGDIOBJ hLastPen = SelectObject(hdc, hNullPen)) { if (HGDIOBJ hOldBrush = SelectObject(hdc, GetStockObject(BLACK_BRUSH))) { const int tickHeight = mTickArea.bottom - mTickArea.top; const POINT pts1[3]={ { selx1+1, mTickArea.top }, { selx1+1, mTickArea.bottom }, { selx1+1-tickHeight, mTickArea.top }, }; const POINT pts2[3]={ { selx2, mTickArea.top }, { selx2, mTickArea.bottom }, { selx2+tickHeight, mTickArea.top }, }; Polygon(hdc, pts1, 3); Polygon(hdc, pts2, 3); SelectObject(hdc, hOldBrush); } SelectObject(hdc, hLastPen); } DeleteObject(hNullPen); } } // Draw track border. const int xedge = GetSystemMetrics(SM_CXEDGE); const int yedge = GetSystemMetrics(SM_CYEDGE); RECT rEdge = mTrack; InflateRect(&rEdge, xedge, yedge); DrawEdge(hdc, &rEdge, EDGE_SUNKEN, BF_RECT); // Draw cursor. RECT rThumb = mThumbRect; DrawEdge(hdc, &rThumb, EDGE_RAISED, BF_SOFT|BF_RECT|BF_ADJUST); DrawEdge(hdc, &rThumb, EDGE_SUNKEN, BF_SOFT|BF_RECT|BF_ADJUST); // All done. SelectObject(hdc, hOldPen); SelectObject(hdc, hOldFont); EndPaint(mhwnd, &ps); }
BOOL FAR PASCAL LEDWndProc( IN HWND hwnd, IN DWORD message, IN DWORD wParam, IN LONG lParam ) /*++ Routine Description: This routine handles the WM_PAINT and WM_SETTEXT messages for the "LED" display window. Arguments: hwnd - supplies a handle to the window to draw into message - supplies the window message to the window pointed to be "hwnd" wParam - supplies the word parameter for the message in "message" lParam - supplies the long parameter for the message in "message" Return Value: Whatever our call to DefWindowProc returns for this window. --*/ { HDC hdc; PAINTSTRUCT ps; RECT r,r1; CHAR s[50]; BOOL b; switch( message ) { case WM_PAINT: // // Set up to draw into this window // hdc = BeginPaint( hwnd, &ps ); GetClientRect( hwnd, &r ); // // Draw black background // SelectObject( hdc, (HGDIOBJ)hLEDFont ); SetBkColor( hdc, cdBLACK ); SetTextColor( hdc, RGB(0x80,0x80,0x00) ); ExtTextOut( hdc, 0, 0, ETO_OPAQUE, (CONST RECT *)&r, NULL, 0, NULL ); // // The bottom and right borders are not drawn -- they are // used for alignment, so move our client rectangle in // so that it only encompasses the "drawable" area. // r.bottom--; r.right--; // // Draw Text // InflateRect( &r, -1, -1 ); CopyRect( &r1, (CONST RECT *)&r ); GetWindowText( gLEDWnd, s, 50 ); DrawText( hdc, s, strlen(s), &r1, DT_CALCRECT | DT_SINGLELINE ); OffsetRect( &r1, (((r.right-r.left)-(r1.right-r1.left))/2), (((r.bottom-r.top)-(r1.bottom-r1.top))/2)-2 ); ExtTextOut( hdc, r1.left, r1.top, ETO_OPAQUE, (CONST RECT *)&r1, s, strlen(s), NULL ); // // Draw Borders // // InflateRect( &r, 1, 1 ); SelectObject( hdc, (HGDIOBJ)hpDkGray ); MoveToEx( hdc, r.left, r.bottom, NULL ); LineTo( hdc, r.left, r.top ); LineTo( hdc, r.right, r.top ); SelectObject( hdc, (HGDIOBJ)hpWhite ); LineTo( hdc, r.right, r.bottom ); LineTo( hdc, r.left, r.bottom ); EndPaint( hwnd, (CONST PAINTSTRUCT *)&ps ); return( 0 ); break; case WM_SETTEXT: // // Set up to draw into this window // hdc = GetDC( hwnd ); GetClientRect( hwnd, &r ); // // The bottom and right borders are not drawn -- they are // used for alignment, so move our client rectangle in // so that it only encompasses the "drawable" area. // r.bottom--; r.right--; // // Draw text // InflateRect( &r, -1, -1 ); SetBkColor( hdc, cdBLACK ); SetTextColor( hdc, RGB(0x80,0x80,0x00) ); SelectObject( hdc, (HGDIOBJ)hLEDFont ); CopyRect( &r1, (CONST RECT *)&r ); DrawText( hdc, (LPSTR)lParam, strlen((LPSTR)lParam), &r1, DT_CALCRECT | DT_SINGLELINE); OffsetRect( &r1, (((r.right-r.left)-(r1.right-r1.left))/2), (((r.bottom-r.top)-(r1.bottom-r1.top))/2)-2 ); r1.right+=5; ExtTextOut( hdc, r1.left, r1.top, ETO_OPAQUE, (CONST RECT *)&r1, (LPSTR)lParam, strlen((LPSTR)lParam), NULL ); ReleaseDC( hwnd, hdc ); break; case WM_LBUTTONUP: b = gDisplayDr; gDisplayDr = gDisplayTr; gDisplayTr = gDisplayT; gDisplayT = b; CheckAndSetControls(); UpdateDisplay( DISPLAY_UPD_LED ); break; } return( DefWindowProc( hwnd, message, wParam, lParam ) ); }
void CStatusWindow::redraw() { // if ( !ToolCanDraw() ) // return; if ( !m_pScrollbar ) return; CDrawHelper helper( this, RGB( 0, 0, 0 ) ); RECT rc; helper.GetClientRect( rc ); RECT rcText = rc; int lineheight = ( STATUS_FONT_SIZE + 2 ); InflateRect( &rcText, -4, 0 ); rcText.bottom = h2() - 4; rcText.top = rcText.bottom - lineheight; int minval = m_pScrollbar->getMinValue(); int maxval = m_pScrollbar->getMaxValue(); int pagesize = m_pScrollbar->getPagesize(); int curval = m_pScrollbar->getValue(); int offset = ( maxval - pagesize ) - curval; offset = ( offset + lineheight - 1 ) / lineheight; offset = max( 0, offset ); //offset = 0; //offset += 10; //offset = max( 0, offset ); for ( int i = 0; i < MAX_TEXT_LINES - offset; i++ ) { int rawline = m_nCurrentLine - i - 1; if ( rawline <= 0 ) continue; if ( rcText.bottom < 0 ) break; int line = ( rawline - offset ) & TEXT_LINE_MASK; COLORREF clr = RGB( m_rgTextLines[ line ].r, m_rgTextLines[ line ].g, m_rgTextLines[ line ].b ); char *ptext = m_rgTextLines[ line ].m_szText; RECT rcTime = rcText; rcTime.right = rcTime.left + 50; char sz[ 32 ]; sprintf( sz, "%.3f", m_rgTextLines[ line ].curtime ); int len = helper.CalcTextWidth( "Arial", STATUS_FONT_SIZE, FW_NORMAL, sz ); rcTime.left = rcTime.right - len - 5; helper.DrawColoredText( "Arial", STATUS_FONT_SIZE, FW_NORMAL, RGB( 255, 255, 150 ), rcTime, sz ); rcTime = rcText; rcTime.left += 50; helper.DrawColoredText( "Arial", STATUS_FONT_SIZE, FW_NORMAL, clr, rcTime, ptext ); OffsetRect( &rcText, 0, -lineheight ); } }
BOOL CItemList::DrawItem( DWORD i, HDC hDC, LPRECT pRect) { CText text; RECT rect; LPLISTSUBITEMINFO plsii = m_pIndex[ i ]->head; LPHEADERITEMINFO phii = NULL; text.SetFlags( DT_SINGLELINE | DT_VCENTER ); text.SetColor( m_rgbText ); // Use bold text for group names if ( ( m_pIndex[ i ]->flags & LIF_GROUP ) != 0 ) text.SetWeight( FW_BOLD ); // Rect CopyRect( &rect, pRect ); InflateRect( &rect, 0, -1 ); if ( ( m_pIndex[ i ]->flags & LIF_SELECTED ) != 0 && ( m_pIndex[ i ]->flags & LIF_GROUP ) == 0 ) { CGrDC::VertGradientFill( hDC, &rect, m_rgbSelTop, m_rgbSelBottom ); } // end if // Adjust for horz scroll rect.left -= m_lHScroll; // rect.top += 1; BOOL bSpecialFont = TRUE; // Draw all items while ( ( phii = m_header.GetNext( phii ) ) != NULL && plsii != NULL && rect.left < pRect->right ) { // Set special font if ( plsii->pfont != NULL ) { bSpecialFont = TRUE; text.SetFont( plsii->pfont ); } // Set default font else if ( bSpecialFont ) { bSpecialFont = FALSE; text.SetFont( 16, "Arial" ); } if ( m_bGroups && ( m_pIndex[ i ]->flags & LIF_GROUP ) != 0 ) rect.right = pRect->right; else { // Calculate item width rect.right = rect.left + phii->width; if ( rect.right > pRect->right ) rect.right = pRect->right; } // end else if ( rect.right > pRect->left ) { // Fill in bck if needed if ( ( m_pIndex[ i ]->flags & LIF_SELECTED ) != 0 && ( m_pIndex[ i ]->flags & LIF_GROUP ) == 0 ) { if ( plsii->rgbbck != MAXDWORD ) { RECT b; CopyRect( &b, &rect ); InflateRect( &b, -2, -1 ); b.top++; b.right--; CGrDC::FillSolidRect( hDC, &b, plsii->rgbbck ); // COLORREF bottom = CGrDC::ScaleColor( plsii->rgbbck, -50 ); // CGrDC::GradientFill( hDC, &rect, plsii->rgbbck, bottom ); } // end if } // end if else { if ( plsii->rgbbck != MAXDWORD ) { RECT b; CopyRect( &b, &rect ); InflateRect( &b, -2, -1 ); b.top++; b.right--; CGrDC::FillSolidRect( hDC, &b, plsii->rgbbck ); // CGrDC::GradientFill( hDC, &rect, plsii->rgbbck, m_rgbSelBottom ); } // end if } // end else // Draw icon if needed if ( plsii->icon != NULL ) { DrawIconEx( hDC, rect.left + 2, rect.top + 2, plsii->icon, 16, 16, 0, NULL, DI_NORMAL ); rect.left += 17; } // end if if ( plsii->type == SIT_TEXT ) { rect.left += 3; // Did the user specify a color? if ( plsii->rgbtext != MAXDWORD ) text.SetColor( plsii->rgbtext ); // Is Item selected? else if ( ( m_pIndex[ i ]->flags & LIF_SELECTED ) != 0 && ( m_pIndex[ i ]->flags & LIF_GROUP ) == 0 ) text.SetColor( m_rgbSelText ); // Set default text color else text.SetColor( m_rgbText ); text.DrawText( hDC, (char*)plsii->data, &rect ); } // end if } // end if // Shift rect rect.left = rect.right; // Next sub-item plsii = plsii->pNext; } // end while return TRUE; }
BOOL CItemList::Draw(HDC hDC, LPRECT pRect, HWND hWnd ) { // Reset default colors if needed if ( m_bAutoDefaultColors ) DefaultColors(); // Check for no draw if ( m_dwNoDraw ) { m_dwNoDraw--; return TRUE; } RECT draw; CopyRect( &draw, pRect ); // Fill in the back ground CGrDC::VertGradientFill( hDC, &draw, m_rgbBckTop, m_rgbBckBottom ); // Draw side bar if ( m_bGroups ) { draw.right = draw.left + GROUPOFFSET; CGrDC::VertGradientFill( hDC, &draw, m_rgbBarTop, m_rgbBarBottom ); CopyRect( &draw, pRect ); } // end if // Draw the header m_header.Draw( hDC, &draw, m_lHScroll, m_bGroups ? GROUPOFFSET : 0 ); // Draw line under header CGrDC::Line( hDC, m_rgbHorzLines, 1, draw.left, draw.top + m_header.GetHeight(), draw.right, draw.top + m_header.GetHeight() ); // Offset header for groups if needed if ( m_bGroups ) draw.left += GROUPOFFSET; // Offset the rect below the header draw.top += m_header.GetHeight(); if ( draw.top >= draw.bottom ) return TRUE; // Item rect RECT ir; ir.left = draw.left; ir.top = draw.top; ir.right = draw.right; ir.bottom = draw.top; BOOL bCollapsed = FALSE; DWORD i = 0; if ( !m_bGroups ) i = m_dwLine; else while ( i < m_dwLine && i < m_dwPtr ) { if ( m_pIndex[ i ] != NULL ) { if ( ( m_pIndex[ i ]->flags & LIF_GROUP ) != 0 ) { if ( ( m_pIndex[ i ]->flags & LIF_COLLAPSED ) != 0 ) bCollapsed = TRUE; else bCollapsed = FALSE; } // end if } // end if i++; } // end while while ( i < m_dwPtr && ir.bottom < pRect->bottom ) { LPLISTITEMINFO plii = m_pIndex[ i ]; // Skip collapsed items if ( bCollapsed ) while ( plii != NULL && ( plii->flags & LIF_GROUP ) == 0 ) if ( ++i < m_dwPtr ) plii = m_pIndex[ i ]; else plii = NULL; if ( plii != NULL ) { // Calculate list item height ir.bottom = ir.top + plii->height; if ( m_bGroups && ( plii->flags & LIF_GROUP ) == 0 ) { CGrDC::FillSolidRect( hDC, &ir, GetSysColor( COLOR_WINDOW ) ); } // end if // if ( ir.bottom < pRect->bottom ) { // Draw tab if ( m_bGroups && ( plii->flags & LIF_GROUP ) != 0 ) { RECT tab; CopyRect( &tab, &ir ); tab.left = pRect->left; tab.right = ir.left - 1; tab.bottom = tab.top + RW( tab ); InflateRect( &tab, -2, -2 ); CGrDC::Center( &tab, &ir, FALSE, TRUE ); // Are we using XP themes? // if ( FALSE ) if ( CXpTheme::IsWindowThemed( hWnd ) ) { CXpTheme xpthm( hWnd, "TREEVIEW" ); if ( ( plii->flags & LIF_COLLAPSED ) != 0 ) xpthm.DrawThemeBackground( hDC, TVP_GLYPH, GLPS_CLOSED, &tab, NULL ); else xpthm.DrawThemeBackground( hDC, TVP_GLYPH, GLPS_OPENED, &tab, NULL ); } // end if else { CGrDC::FillSolidRect( hDC, &tab, m_rgbBckTop ); CGrDC::Box3d( hDC, &tab, 1, RGB( 0, 0, 0 ), RGB( 0, 0, 0 ) ); long mh = tab.top + ( RH( tab ) / 2 ); long mw = tab.left + ( RW( tab ) / 2 ); CGrDC::Line( hDC, RGB( 0, 0, 0 ), 1, tab.left + 2, mh, tab.right - 2, mh ); if ( ( plii->flags & LIF_COLLAPSED ) != 0 ) CGrDC::Line( hDC, RGB( 0, 0, 0 ), 1, mw, tab.top + 2, mw, tab.bottom - 2 ); } // end else } // end if // Draw this list item DrawItem( i, hDC, &ir ); if ( m_bHorzLines ) { CGrDC::Line( hDC, m_rgbHorzLines, 1, ir.left, ir.top, ir.right, ir.top ); if ( m_bGroups && ( plii->flags & LIF_GROUP ) != 0 && ( plii->flags & LIF_COLLAPSED ) != 0 ) { HPEN hPen = CreatePen( PS_SOLID, 1, m_rgbSelTop ); HPEN hOldPen = (HPEN)::SelectObject( hDC, hPen ); COLORREF oldcolor = SetBkColor( hDC, m_rgbBckTop ); MoveToEx( hDC, ir.left, ir.bottom - 1, NULL ); LineTo( hDC, ir.right, ir.bottom - 1 ); ::SelectObject( hDC, hOldPen ); ::DeleteObject( hPen ); hPen = CreatePen( PS_SOLID, 1, RGB( 220, 220, 220 ) ); hOldPen = (HPEN)::SelectObject( hDC, hPen ); MoveToEx( hDC, ir.left, ir.bottom - 2, NULL ); LineTo( hDC, ir.right, ir.bottom - 2 ); // Release drawing objects SetBkColor( hDC, oldcolor ); ::SelectObject( hDC, hOldPen ); ::DeleteObject( hPen ); } // end else // CGrDC::Box3d( hDC, &ir, 1, m_rgbHorzLines, m_rgbHorzLines ); } // end if if ( m_bVertLines && ( plii->flags & LIF_GROUP ) == 0 ) { long x = ir.left; CGrDC::Line( hDC, m_rgbHorzLines, 1, x, ir.top, x, ir.bottom ); x--; LPHEADERITEMINFO phii = NULL; while( ( phii = GetHeader().GetNext( phii ) ) != NULL && GetHeader().GetNext( phii ) != NULL ) { // Add width x += phii->width; // Draw vertical line CGrDC::Line( hDC, m_rgbHorzLines, 1, x, ir.top, x, ir.bottom ); } // end while CGrDC::Line( hDC, m_rgbHorzLines, 1, ir.right - 1, ir.top, ir.right - 1, ir.bottom ); } // end if } // end if // Next item position ir.top = ir.bottom; // Are we collapsing? if ( ( plii->flags & LIF_GROUP ) != 0 ) { if ( ( plii->flags & LIF_COLLAPSED ) != 0 ) bCollapsed = TRUE; else bCollapsed = FALSE; } // end if } // end if // Next item i++; } // end while // Draw last horz line if ( m_bHorzLines ) CGrDC::Line( hDC, m_rgbHorzLines, 1, ir.left, ir.bottom, ir.right, ir.bottom ); /* if ( m_bVertLines ) { long x = draw.left; CGrDC::Line( hDC, m_rgbHorzLines, 1, x, draw.top, x, ir.bottom ); x--; LPHEADERITEMINFO phii = NULL; while( ( phii = GetHeader().GetNext( phii ) ) != NULL ) { // Add width x += phii->width; // Draw vertical line CGrDC::Line( hDC, m_rgbHorzLines, 1, x, draw.top, x, ir.bottom ); } // end while } // end if */ return TRUE; }
bool Balloon::DrawAlphaBlend() { RECT clientrt, contentrt; POINT srcPt; SIZE wndSz; BLENDFUNCTION bf; CLIENTINFO clientInfo; FORMATINFO formatInfo; int alpha = (pSettings->GetAlpha() * 255) / 100; if (!GetClientRect(balloonWnd, &clientrt)) { return false; } HDC hdc = CreateCompatibleDC(NULL); HBITMAP hbitmap = EGCreateBitmap(0x00, RGB(0, 0, 0), clientrt); HGDIOBJ hobj = SelectObject(hdc, hbitmap); CopyRect(&contentrt, &clientrt); EGFrameRect(hdc, &contentrt, 255, pSettings->GetBorderColor(), 1); InflateRect(&contentrt, -1, -1); if (ELToLower(pSettings->GetGradientMethod()) == TEXT("solid")) { EGFillRect(hdc, &clientrt, alpha, pSettings->GetGradientFrom()); } else EGGradientFillRect(hdc, &contentrt, alpha, pSettings->GetGradientFrom(), pSettings->GetGradientTo(), 0, pSettings->GetGradientMethod()); formatInfo.horizontalAlignment = EGDAT_LEFT; formatInfo.verticalAlignment = EGDAT_TOP; formatInfo.font = CreateFontIndirect(pSettings->GetInfoFont()); formatInfo.color = pSettings->GetTextColor(); formatInfo.flags = DT_WORDBREAK; clientInfo.hdc = hdc; CopyRect(&clientInfo.rt, &infoRect); clientInfo.bgAlpha = alpha; EGDrawAlphaText(255, clientInfo, formatInfo, info); DeleteObject(formatInfo.font); formatInfo.font = CreateFontIndirect(pSettings->GetInfoTitleFont()); formatInfo.flags = DT_SINGLELINE; CopyRect(&clientInfo.rt, &titleRect); EGDrawAlphaText(255, clientInfo, formatInfo, infoTitle); DeleteObject(formatInfo.font); if (icon) { DrawIconEx(hdc, 5, 5, icon, iconWidth, iconHeight, 0, NULL, DI_NORMAL); } bf.BlendOp = AC_SRC_OVER; bf.BlendFlags = 0; bf.AlphaFormat = AC_SRC_ALPHA; // use source alpha bf.SourceConstantAlpha = 255; wndSz.cx = clientrt.right; wndSz.cy = clientrt.bottom; srcPt.x = 0; srcPt.y = 0; UpdateLayeredWindow(balloonWnd, NULL, NULL, &wndSz, hdc, &srcPt, 0, &bf, ULW_ALPHA); // do cleanup SelectObject(hdc, hobj); DeleteDC(hdc); DeleteObject(hbitmap); return true; }
void fsODMenu::OnDrawItem(LPDRAWITEMSTRUCT pdis) { CDC *dc = CDC::FromHandle (pdis->hDC); fsODMenuItemData* pData = (fsODMenuItemData*) pdis->itemData; UINT uState = pdis->itemState; CFont *oldfont = dc->SelectObject (pData->bBold ? &m_fontBold : &m_font); RECT rcItem = pdis->rcItem; RECT rcIcon = rcItem; rcIcon.left += 3; rcIcon.right = rcIcon.left + m_cxIcon; rcIcon.top += (rcIcon.bottom - rcIcon.top - m_cyIcon) / 2; rcIcon.bottom = rcIcon.top + m_cyIcon; RECT rcIconFrame = rcIcon; InflateRect (&rcIconFrame, 2, 2); RECT rcSel; if (pData->bMenuBar) { rcSel = pdis->rcItem; InflateRect (&rcSel, -1, -1); fsFillSolidRect (dc, &rcItem, GetSysColor (COLOR_3DFACE)); } else { rcSel = rcIconFrame; rcSel.right = rcItem.right; rcSel.bottom++; fsFillSolidRect (dc, &rcItem, GetSysColor (COLOR_MENU)); rcItem.left += m_cxIcon; } if (pData->strMenuText.GetLength () == 0) { RECT rect = rcItem; rect.left -= m_cxIcon; rect.top += (rect.bottom - rect.top) / 2; rect.bottom = rect.top+1; rect.right = rcItem.right; fsFillSolidRect (dc, &rect, GetSysColor (COLOR_GRAYTEXT)); return; } if (uState & 0x40 ) if (pData->bMenuBar) fsDrawFrame (dc, &rcSel, 1); if (uState & ODS_SELECTED) { if (pData->bMenuBar) fsDrawPressedFrame (dc, &rcSel, 1); else { fsFillSolidRect (dc, &rcSel, GetSysColor (COLOR_HIGHLIGHT)); } } dc->SetBkMode (TRANSPARENT); if (pData->bMenuBar) { if (uState & ODS_GRAYED || uState & ODS_DISABLED) dc->SetTextColor (GetSysColor (COLOR_GRAYTEXT)); dc->DrawText (pData->strMenuText, &rcItem, DT_VCENTER | DT_SINGLELINE | DT_CENTER); } else { CPen pen (PS_SOLID, 1, GetSystemMetrics (COLOR_HIGHLIGHTTEXT)); CPen *oldpen = dc->SelectObject (&pen); if (uState & ODS_GRAYED || uState & ODS_DISABLED) dc->SetTextColor (GetSysColor (COLOR_GRAYTEXT)); else if (uState & ODS_SELECTED) dc->SetTextColor (GetSysColor (COLOR_HIGHLIGHTTEXT)); else dc->SetTextColor (GetSysColor (COLOR_MENUTEXT)); LPCSTR pszTab = strchr (pData->strMenuText, '\t'); int left = pszTab ? pszTab - pData->strMenuText : pData->strMenuText.GetLength (); rcItem.left += 9; rcItem.right -= 15; dc->DrawText (pData->strMenuText, left, &rcItem, DT_VCENTER | DT_SINGLELINE); if (pszTab) dc->DrawText (pszTab+1, -1, &rcItem, DT_VCENTER | DT_SINGLELINE | DT_RIGHT); dc->SelectObject (oldpen); } POINT ptIcon; ptIcon.x = rcIcon.left + 1; ptIcon.y = rcIcon.top + 1; RECT rcClr = pdis->rcItem; rcClr.right = m_cxIcon + 5; if (uState & ODS_CHECKED) { if (pData->iCheckImage >= 0) { fsFillSolidRect (dc, &rcClr, GetSysColor (COLOR_MENU)); m_pImages->Draw (dc, pData->iCheckImage, ptIcon, ILD_TRANSPARENT); } else if (pData->iImage >= 0) { fsFillSolidRect (dc, &rcClr, GetSysColor (COLOR_MENU)); rcIconFrame.right--; fsDrawPressedFrame (dc, &rcIconFrame, 1); m_pImages->Draw (dc, pData->iImage, ptIcon, ILD_TRANSPARENT); } else { CFont font; char check; int fsize; switch (pData->iCheckImage) { case ODMENU_CHECKIMAGE_CHECK: { DrawCheckMark (dc, rcIcon, uState & ODS_SELECTED, uState & ODS_GRAYED); } break; case ODMENU_CHECKIMAGE_RADIO: { check = 105; fsize = m_cyIcon; font.CreateFont (fsize, 0, 0, 0, FW_NORMAL, 0, 0, 0, DEFAULT_CHARSET, 0, 0, 0, 0, "Marlett"); CFont* oldfont = dc->SelectObject (&font); dc->DrawText (&check, 1, &rcIcon, DT_SINGLELINE | DT_CENTER | DT_VCENTER); dc->SelectObject (oldfont); } break; default: return; } } } else if (pData->iImage != -1) { fsFillSolidRect (dc, &rcClr, GetSysColor (COLOR_MENU)); if (uState & ODS_GRAYED || uState & ODS_DISABLED) { if (m_pDisImages == NULL) { HICON hI = m_pImages->ExtractIcon (pData->iImage); DrawState (dc->m_hDC, NULL, NULL, LPARAM (hI), 0, ptIcon.x, ptIcon.y, m_cxIcon, m_cyIcon, DST_ICON | DSS_DISABLED); DestroyIcon (hI); } else m_pDisImages->Draw (dc, pData->iImage, ptIcon, ILD_TRANSPARENT); } else { if (uState & ODS_SELECTED) fsDrawFrame (dc, &rcIconFrame, 1); m_pImages->Draw (dc, pData->iImage, ptIcon, ILD_TRANSPARENT); } } dc->SelectObject (oldfont); }
void CDlgTabFrame::Size() { CWnd *pTab = GetDlgItem( IDC_TAB ); CWnd *pBlank = GetDlgItem( IDC_BLANK ); RECT rect; if ( m_bSize ) { GetClientRect( &rect ); InflateRect( &rect, -4, -4 ); // Set tab control position if ( pTab != NULL ) { pTab->SetWindowPos( NULL, rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top, SWP_NOZORDER | SWP_NOACTIVATE ); } // end if } // end if // Adjust window to tab control if ( pTab != NULL && ::IsWindow( pTab->GetSafeHwnd() ) ) { if ( !m_bSize ) { pTab->GetWindowRect( &rect ); ScreenToClient( &rect ); } // end if m_tab.AdjustRect( FALSE, &rect ); rect.bottom -= 2; // Set page parent window position if ( pBlank != NULL ) { // Set page parent position pBlank->SetWindowPos( NULL, rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top, SWP_NOZORDER | SWP_NOACTIVATE ); m_blank.GetClientRect( &rect ); // m_blank.GetWindowRect( &rect ); // ScreenToClient( &rect ); } // end if // Set page window position if ( m_pg[ m_dwPg ] != NULL && ::IsWindow( m_pg[ m_dwPg ]->GetSafeHwnd() ) ) { // Set the page position m_pg[ m_dwPg ]->SetWindowPos( NULL, rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top, SWP_NOZORDER | SWP_NOACTIVATE ); m_pg[ m_dwPg ]->RedrawWindow(); } // end if } // end if }
LRESULT AeroControlBase::ButtonWindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { switch(uMsg) { case WM_SETTEXT: case WM_ENABLE: case WM_STYLECHANGED: { LRESULT res = DefSubclassProc(hWnd, uMsg, wParam, lParam); InvalidateRgn(hWnd, NULL, FALSE); return res; } break; case WM_PAINT: { PAINTSTRUCT ps; HDC hdc = BeginPaint(hWnd, &ps); if(hdc) { LONG_PTR dwStyle = GetWindowLongPtr(hWnd, GWL_STYLE); LONG_PTR dwButtonStyle = LOWORD(dwStyle); LONG_PTR dwButtonType = dwButtonStyle&0xF; RECT rcClient; VERIFY(GetClientRect(hWnd, &rcClient)); if((dwButtonType&BS_GROUPBOX)==BS_GROUPBOX) { /// /// it must be a group box /// HTHEME hTheme = OpenThemeData(hWnd, L"Button"); if(hTheme) { BP_PAINTPARAMS params = { sizeof(BP_PAINTPARAMS) }; params.dwFlags = BPPF_ERASE; RECT rcExclusion = rcClient; params.prcExclude = &rcExclusion; /// /// We have to calculate the exclusion rect and therefore /// calculate the font height. We select the control's font /// into the DC and fake a drawing operation: /// HFONT hFontOld = (HFONT)SendMessage(hWnd, WM_GETFONT, 0L, NULL); if(hFontOld) hFontOld = (HFONT) SelectObject(hdc, hFontOld); RECT rcDraw = rcClient; DWORD dwFlags = DT_SINGLELINE; /// /// we use uppercase A to determine the height of text, so we /// can draw the upper line of the groupbox: /// DrawTextW(hdc, L"A", -1, &rcDraw, dwFlags|DT_CALCRECT); if (hFontOld) { SelectObject(hdc, hFontOld); hFontOld = NULL; } VERIFY(InflateRect(&rcExclusion, -1, -1*RECTHEIGHT(rcDraw))); HDC hdcPaint = NULL; HPAINTBUFFER hBufferedPaint = BeginBufferedPaint(hdc, &rcClient, BPBF_TOPDOWNDIB, ¶ms, &hdcPaint); if (hdcPaint) { /// /// now we again retrieve the font, but this time we select it into /// the buffered DC: /// hFontOld = (HFONT)SendMessage(hWnd, WM_GETFONT, 0L, NULL); if(hFontOld) hFontOld = (HFONT) SelectObject(hdcPaint, hFontOld); VERIFY(PatBlt(hdcPaint, 0, 0, RECTWIDTH(rcClient), RECTHEIGHT(rcClient), BLACKNESS)); VERIFY(S_OK==BufferedPaintSetAlpha(hBufferedPaint, &ps.rcPaint, 0x00)); int iPartId = BP_GROUPBOX; int iState = GetStateFromBtnState(dwStyle, FALSE, FALSE, 0L, iPartId, FALSE); DTTOPTS DttOpts = {sizeof(DTTOPTS)}; DttOpts.dwFlags = DTT_COMPOSITED | DTT_GLOWSIZE; DttOpts.crText = RGB(255, 255, 255); DttOpts.iGlowSize = 12; // Default value VERIFY(DetermineGlowSize(&DttOpts.iGlowSize)); COLORREF cr = RGB(0x00, 0x00, 0x00); VERIFY(GetEditBorderColor(hWnd, &cr)); /// /// add the alpha value: /// cr |= 0xff000000; std::unique_ptr<Pen> myPen( new Pen(Color(cr), 1) ); std::unique_ptr<Graphics> myGraphics( new Graphics(hdcPaint) ); int iY = RECTHEIGHT(rcDraw)/2; Rect rr = Rect(rcClient.left, rcClient.top+iY, RECTWIDTH(rcClient), RECTHEIGHT(rcClient)-iY-1); GraphicsPath path; GetRoundRectPath(&path, rr, 10); myGraphics->DrawPath(myPen.get(), &path); //myGraphics->DrawRectangle(myPen, rcClient.left, rcClient.top + iY, // RECTWIDTH(rcClient)-1, RECTHEIGHT(rcClient) - iY-1); myGraphics.reset(); myPen.reset(); int iLen = GetWindowTextLength(hWnd); if(iLen) { iLen+=5; // 1 for terminating zero, 4 for DT_MODIFYSTRING LPWSTR szText = (LPWSTR)LocalAlloc(LPTR, sizeof(WCHAR)*iLen); if(szText) { iLen = GetWindowTextW(hWnd, szText, iLen); if(iLen) { int iX = RECTWIDTH(rcDraw); rcDraw = rcClient; rcDraw.left += iX; DrawTextW(hdcPaint, szText, -1, &rcDraw, dwFlags|DT_CALCRECT); VERIFY(PatBlt(hdcPaint, rcDraw.left, rcDraw.top , RECTWIDTH(rcDraw) + 3, RECTHEIGHT(rcDraw), BLACKNESS)); rcDraw.left++; rcDraw.right++; VERIFY(S_OK==DrawThemeTextEx(hTheme, hdcPaint, iPartId, iState, szText, -1, dwFlags, &rcDraw, &DttOpts)); } VERIFY(!LocalFree(szText)); } } if (hFontOld) { SelectObject(hdcPaint, hFontOld); hFontOld = NULL; } VERIFY(S_OK==EndBufferedPaint(hBufferedPaint, TRUE)); } VERIFY(S_OK==CloseThemeData(hTheme)); } } else if(dwButtonType==BS_CHECKBOX || dwButtonType==BS_AUTOCHECKBOX || dwButtonType==BS_3STATE || dwButtonType==BS_AUTO3STATE || dwButtonType==BS_RADIOBUTTON || dwButtonType==BS_AUTORADIOBUTTON) { HTHEME hTheme = OpenThemeData(hWnd, L"Button"); if(hTheme) { HDC hdcPaint = NULL; BP_PAINTPARAMS params = { sizeof(BP_PAINTPARAMS) }; params.dwFlags = BPPF_ERASE; HPAINTBUFFER hBufferedPaint = BeginBufferedPaint(hdc, &rcClient, BPBF_TOPDOWNDIB, ¶ms, &hdcPaint); if (hdcPaint) { VERIFY(PatBlt(hdcPaint, 0, 0, RECTWIDTH(rcClient), RECTHEIGHT(rcClient), BLACKNESS)); VERIFY(S_OK==BufferedPaintSetAlpha(hBufferedPaint, &ps.rcPaint, 0x00)); LRESULT dwCheckState = SendMessage(hWnd, BM_GETCHECK, 0, NULL); POINT pt; RECT rc; GetWindowRect(hWnd, &rc); GetCursorPos(&pt); BOOL bHot = PtInRect(&rc, pt); BOOL bFocus = GetFocus()==hWnd; int iPartId = BP_CHECKBOX; if(dwButtonType==BS_RADIOBUTTON || dwButtonType==BS_AUTORADIOBUTTON) iPartId = BP_RADIOBUTTON; int iState = GetStateFromBtnState(dwStyle, bHot, bFocus, dwCheckState, iPartId, FALSE); int bmWidth = int(ceil(13.0 * GetDeviceCaps(hdcPaint, LOGPIXELSX) / 96.0)); UINT uiHalfWidth = (RECTWIDTH(rcClient) - bmWidth)/2; /// /// we have to use the whole client area, otherwise we get only partially /// drawn areas: /// RECT rcPaint = rcClient; if(dwButtonStyle & BS_LEFTTEXT) { rcPaint.left += uiHalfWidth; rcPaint.right += uiHalfWidth; } else { rcPaint.left -= uiHalfWidth; rcPaint.right -= uiHalfWidth; } /// /// we assume that bmWidth is both the horizontal and the vertical /// dimension of the control bitmap and that it is square. bm.bmHeight /// seems to be the height of a striped bitmap because it is an absurdly /// high dimension value /// if((dwButtonStyle&BS_VCENTER)==BS_VCENTER) /// BS_VCENTER is BS_TOP|BS_BOTTOM { int h = RECTHEIGHT(rcPaint); rcPaint.top = (h - bmWidth) / 2; rcPaint.bottom = rcPaint.top + bmWidth; } else if(dwButtonStyle&BS_TOP) { rcPaint.bottom = rcPaint.top + bmWidth; } else if(dwButtonStyle&BS_BOTTOM) { rcPaint.top = rcPaint.bottom - bmWidth; } else // default: center the checkbox/radiobutton vertically { int h = RECTHEIGHT(rcPaint); rcPaint.top = (h - bmWidth) / 2; rcPaint.bottom = rcPaint.top + bmWidth; } VERIFY(S_OK==DrawThemeBackground(hTheme, hdcPaint, iPartId, iState, &rcPaint, NULL)); rcPaint = rcClient; VERIFY(S_OK==GetThemeBackgroundContentRect(hTheme, hdcPaint, iPartId, iState, &rcPaint, &rc)); if(dwButtonStyle & BS_LEFTTEXT) rc.right -= bmWidth + 2 * GetSystemMetrics(SM_CXEDGE); else rc.left += bmWidth + 2 * GetSystemMetrics(SM_CXEDGE); DTTOPTS DttOpts = {sizeof(DTTOPTS)}; DttOpts.dwFlags = DTT_COMPOSITED | DTT_GLOWSIZE; DttOpts.crText = RGB(255, 255, 255); DttOpts.iGlowSize = 12; // Default value VERIFY(DetermineGlowSize(&DttOpts.iGlowSize)); HFONT hFontOld = (HFONT)SendMessage(hWnd, WM_GETFONT, 0L, NULL); if(hFontOld) hFontOld = (HFONT) SelectObject(hdcPaint, hFontOld); int iLen = GetWindowTextLength(hWnd); if(iLen) { iLen+=5; // 1 for terminating zero, 4 for DT_MODIFYSTRING LPWSTR szText = (LPWSTR)LocalAlloc(LPTR, sizeof(WCHAR)*iLen); if(szText) { iLen = GetWindowTextW(hWnd, szText, iLen); if(iLen) { DWORD dwFlags = DT_SINGLELINE /*|DT_VCENTER*/; if(dwButtonStyle&BS_MULTILINE) { dwFlags|=DT_WORDBREAK; dwFlags&= ~(DT_SINGLELINE |DT_VCENTER); } if((dwButtonStyle&BS_CENTER)==BS_CENTER) /// BS_CENTER is BS_LEFT|BS_RIGHT dwFlags|=DT_CENTER; else if(dwButtonStyle&BS_LEFT) dwFlags|=DT_LEFT; else if(dwButtonStyle&BS_RIGHT) dwFlags|=DT_RIGHT; if((dwButtonStyle&BS_VCENTER)==BS_VCENTER) /// BS_VCENTER is BS_TOP|BS_BOTTOM dwFlags|=DT_VCENTER; else if(dwButtonStyle&BS_TOP) dwFlags|=DT_TOP; else if(dwButtonStyle&BS_BOTTOM) dwFlags|=DT_BOTTOM; else dwFlags|=DT_VCENTER; VERIFY(S_OK==DrawThemeTextEx(hTheme, hdcPaint, iPartId, iState, szText, -1, dwFlags, &rc, &DttOpts)); /// /// if our control has the focus, we also have to draw the focus rectangle: /// if(bFocus) { /// /// now calculate the text size: /// RECT rcDraw = rc; /// /// we use GDI's good old DrawText, because it returns much more /// accurate data than DrawThemeTextEx, which takes the glow /// into account which we don't want: /// VERIFY(DrawTextW(hdcPaint, szText, -1, &rcDraw, dwFlags|DT_CALCRECT)); if(dwFlags&DT_SINGLELINE) { dwFlags &= ~DT_VCENTER; RECT rcDrawTop; DrawTextW(hdcPaint, szText, -1, &rcDrawTop, dwFlags|DT_CALCRECT); rcDraw.top = rcDraw.bottom - RECTHEIGHT(rcDrawTop); } if(dwFlags & DT_RIGHT) { int iWidth = RECTWIDTH(rcDraw); rcDraw.right = rc.right; rcDraw.left = rcDraw.right - iWidth; } RECT rcFocus; VERIFY(IntersectRect(&rcFocus, &rc, &rcDraw)); DrawFocusRect(&rcFocus, hdcPaint); } } VERIFY(!LocalFree(szText)); } } if (hFontOld) { SelectObject(hdcPaint, hFontOld); hFontOld = NULL; } VERIFY(S_OK==EndBufferedPaint(hBufferedPaint, TRUE)); } VERIFY(S_OK==CloseThemeData(hTheme)); } } else if(BS_PUSHBUTTON==dwButtonType || BS_DEFPUSHBUTTON==dwButtonType) { /// /// it is a push button /// HTHEME hTheme = OpenThemeData(hWnd, L"Button"); if(hTheme) { HDC hdcPaint = NULL; BP_PAINTPARAMS params = { sizeof(BP_PAINTPARAMS) }; params.dwFlags = BPPF_ERASE; HPAINTBUFFER hBufferedPaint = BeginBufferedPaint(hdc, &rcClient, BPBF_TOPDOWNDIB, ¶ms, &hdcPaint); if (hdcPaint) { VERIFY(PatBlt(hdcPaint, 0, 0, RECTWIDTH(rcClient), RECTHEIGHT(rcClient), BLACKNESS)); VERIFY(S_OK==BufferedPaintSetAlpha(hBufferedPaint, &ps.rcPaint, 0x00)); LRESULT dwCheckState = SendMessage(hWnd, BM_GETCHECK, 0, NULL); POINT pt; RECT rc; GetWindowRect(hWnd, &rc); GetCursorPos(&pt); BOOL bHot = PtInRect(&rc, pt); BOOL bFocus = GetFocus()==hWnd; int iPartId = BP_PUSHBUTTON; if(dwButtonStyle==BS_RADIOBUTTON || dwButtonStyle==BS_AUTORADIOBUTTON) iPartId = BP_RADIOBUTTON; int iState = GetStateFromBtnState(dwStyle, bHot, bFocus, dwCheckState, iPartId, GetCapture()==hWnd); /// /// we have to use the whole client area, otherwise we get only partially /// drawn areas: /// RECT rcPaint = rcClient; VERIFY(S_OK==DrawThemeBackground(hTheme, hdcPaint, iPartId, iState, &rcPaint, NULL)); VERIFY(S_OK==GetThemeBackgroundContentRect(hTheme, hdcPaint, iPartId, iState, &rcPaint, &rc)); DTTOPTS DttOpts = {sizeof(DTTOPTS)}; DttOpts.dwFlags = DTT_COMPOSITED | DTT_GLOWSIZE; DttOpts.crText = RGB(255, 255, 255); DttOpts.iGlowSize = 12; // Default value VERIFY(DetermineGlowSize(&DttOpts.iGlowSize)); HFONT hFontOld = (HFONT)SendMessage(hWnd, WM_GETFONT, 0L, NULL); if(hFontOld) hFontOld = (HFONT) SelectObject(hdcPaint, hFontOld); int iLen = GetWindowTextLength(hWnd); if(iLen) { iLen+=5; // 1 for terminating zero, 4 for DT_MODIFYSTRING LPWSTR szText = (LPWSTR)LocalAlloc(LPTR, sizeof(WCHAR)*iLen); if(szText) { iLen = GetWindowTextW(hWnd, szText, iLen); if(iLen) { DWORD dwFlags = DT_SINGLELINE | DT_CENTER | DT_VCENTER; VERIFY(S_OK==DrawThemeTextEx(hTheme, hdcPaint, iPartId, iState, szText, -1, dwFlags, &rc, &DttOpts)); /// /// if our control has the focus, we also have to draw the focus rectangle: /// if(bFocus) { RECT rcDraw = rcClient; VERIFY(InflateRect(&rcDraw, -3, -3)); DrawFocusRect(&rcDraw, hdcPaint); } } VERIFY(!LocalFree(szText)); } } if (hFontOld) { SelectObject(hdcPaint, hFontOld); hFontOld = NULL; } VERIFY(S_OK==EndBufferedPaint(hBufferedPaint, TRUE)); } VERIFY(S_OK==CloseThemeData(hTheme)); } } else //PaintControl(hWnd, hdc, &ps.rcPaint, (m_dwFlags & WD_DRAW_BORDER)!=0); PaintControl(hWnd, hdc, &ps.rcPaint, false); } EndPaint(hWnd, &ps); return 0; } break; case WM_DESTROY: case WM_NCDESTROY: RemoveWindowSubclass(hWnd, SubclassProc, Button); subclassedControls.erase(hWnd); break; } return DefSubclassProc(hWnd, uMsg, wParam, lParam); }
void CPlaylistWindow_CreateIPEdit(const int iItem, const int iSubItem) { RECT rSubItem; const char* pcClass; DWORD dwStyle; int iSearchItemIDX; UINT uiControlID; BOOL bClearNonSelectedItems; CP_HPLAYLISTITEM hClickedItem; HWND hWndList; int iNumItemsSelected; // If the clicked item is not read/write then skip this hClickedItem = (CP_HPLAYLISTITEM)CLV_GetItemData(globals.m_hPlaylistViewControl, iItem); if (CPLI_GetReadWriteState(hClickedItem) != rwsReadWrite) { MessageBox(windows.m_hWndPlaylist, "This file's ID3 tag cannot be updated. This is because CoolPlayer cannot write to this file.", "Cannot update tag", MB_OK | MB_ICONSTOP); return; } // For some sub items it is not logical to multi update - action these if (iSubItem == PLAYLIST_TITLE) bClearNonSelectedItems = TRUE; else bClearNonSelectedItems = FALSE; // Go through the selected items and remove the selection of items that // cannot be written to (eg because of a read only file) iSearchItemIDX = CLV_GetNextSelectedItem(globals.m_hPlaylistViewControl, CPC_INVALIDITEM); iNumItemsSelected = 1; for (;iSearchItemIDX != -1; iSearchItemIDX = CLV_GetNextSelectedItem(globals.m_hPlaylistViewControl, iSearchItemIDX)) { CP_HPLAYLISTITEM hItem = (CP_HPLAYLISTITEM)CLV_GetItemData(globals.m_hPlaylistViewControl, iSearchItemIDX); CPLI_ReadTag(hItem); // We've already checked this item if (iSearchItemIDX == iItem) continue; iNumItemsSelected++; if (bClearNonSelectedItems == TRUE || CPLI_GetReadWriteState(hItem) != rwsReadWrite) CLV_SetItemSelected(globals.m_hPlaylistViewControl, iSearchItemIDX, FALSE); } // If the "track number" column was clicked - and there are multiple selections - auto number them if (iSubItem == PLAYLIST_TRACKNUM && iNumItemsSelected > 1) { char cStatusMessage[1024]; int iTrackNumber; // Autonumber SetCursor(LoadCursor(NULL, IDC_WAIT)); iSearchItemIDX = CLV_GetNextSelectedItem(globals.m_hPlaylistViewControl, CPC_INVALIDITEM); iTrackNumber = 1; for (;iSearchItemIDX != CPC_INVALIDITEM; iSearchItemIDX = CLV_GetNextSelectedItem(globals.m_hPlaylistViewControl, iSearchItemIDX)) { CP_HPLAYLISTITEM hItem = (CP_HPLAYLISTITEM)CLV_GetItemData(globals.m_hPlaylistViewControl, iSearchItemIDX); sprintf(cStatusMessage, "Tagging \"%s\"", CPLI_GetFilename(hItem)); CP_TRACE1("status: %s", cStatusMessage); CPIC_SetIndicatorValue("status", cStatusMessage); UpdateWindow(IF_GetHWnd(windows.m_hifPlaylist)); CPLI_SetTrackNum(hItem, iTrackNumber); CPLI_WriteTag(hItem); iTrackNumber++; } SetCursor(LoadCursor(NULL, IDC_ARROW)); CPIC_SetIndicatorValue("status", NULL); return; } // If the length was clicked - work out the lengths for all selected items if (iSubItem == PLAYLIST_LENGTH) { char cStatusMessage[1024]; SetCursor(LoadCursor(NULL, IDC_WAIT)); iSearchItemIDX = CLV_GetNextSelectedItem(globals.m_hPlaylistViewControl, CPC_INVALIDITEM); for (; iSearchItemIDX != CPC_INVALIDITEM; iSearchItemIDX = CLV_GetNextSelectedItem(globals.m_hPlaylistViewControl, iSearchItemIDX)) { CP_HPLAYLISTITEM hItem = (CP_HPLAYLISTITEM)CLV_GetItemData(globals.m_hPlaylistViewControl, iSearchItemIDX); CPLI_CalculateLength(hItem); sprintf(cStatusMessage, "Tagging \"%s\"", CPLI_GetFilename(hItem)); CPIC_SetIndicatorValue("status", cStatusMessage); CP_TRACE1("status: %s", cStatusMessage); UpdateWindow(IF_GetHWnd(windows.m_hifPlaylist)); CPLI_WriteTag(hItem); } SetCursor(LoadCursor(NULL, IDC_ARROW)); CPIC_SetIndicatorValue("status", NULL); return; } // We want to get the subitem's rect in the co-ordinate space of the dialog hWndList = CLV_GetHWND(globals.m_hPlaylistViewControl); CLV_GetItemSubRect(globals.m_hPlaylistViewControl, &rSubItem, iItem, iSubItem); ClientToScreen(hWndList, (POINT*)&rSubItem); ClientToScreen(hWndList, ((POINT*)&rSubItem) + 1); ScreenToClient(IF_GetHWnd(windows.m_hifPlaylist), (POINT*)&rSubItem); ScreenToClient(IF_GetHWnd(windows.m_hifPlaylist), ((POINT*)&rSubItem) + 1); if (iSubItem == PLAYLIST_GENRE) { // int iRectHeight = rSubItem.bottom-rSubItem.top; // int iListHeight = iRectHeight<<3; InflateRect(&rSubItem, 2, 2); pcClass = "COMBOBOX"; uiControlID = IDC_PL_FLOATINGCOMBO; dwStyle = CBS_DROPDOWNLIST | CBS_SORT | WS_VSCROLL; rSubItem.bottom += (rSubItem.bottom - rSubItem.top) << 3; } else { InflateRect(&rSubItem, 2, 2); pcClass = "EDIT"; dwStyle = ES_AUTOHSCROLL; uiControlID = IDC_PL_FLOATINGEDIT; if (iSubItem == PLAYLIST_TRACKNUM || iSubItem == PLAYLIST_YEAR) dwStyle |= ES_NUMBER; } // Setup window class and style (the Genre window will be a combo) globals.m_bIP_InhibitUpdates = TRUE; windows.wnd_playlist_IPEdit = CreateWindow(pcClass, "", WS_CHILD | WS_BORDER | WS_CLIPSIBLINGS | dwStyle, rSubItem.left, rSubItem.top, rSubItem.right - rSubItem.left, rSubItem.bottom - rSubItem.top, IF_GetHWnd(windows.m_hifPlaylist), (HMENU)uiControlID, GetModuleHandle(NULL), NULL); SetWindowPos(windows.wnd_playlist_IPEdit, HWND_TOP, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE); ShowWindow(windows.wnd_playlist_IPEdit, SW_SHOW); SetFocus(windows.wnd_playlist_IPEdit); // Setup the font in the control SendMessage(windows.wnd_playlist_IPEdit, WM_SETFONT, (WPARAM)glb_pSkin->mpl_hfFont, MAKELPARAM(TRUE, 0)); // Hook the listview window (so that we can dismiss on VScroll) globals.m_hhkListView_Posted = SetWindowsHookEx(WH_GETMESSAGE, exp_ListViewHookProc_Posted, NULL, GetCurrentThreadId()); // Add the genre items to the list if (iSubItem == PLAYLIST_GENRE) { int iGenreIDX; for (iGenreIDX = 0; iGenreIDX < CIC_NUMGENRES; iGenreIDX++) { int iNewItemIDX = SendMessage(windows.wnd_playlist_IPEdit, CB_ADDSTRING, 0L, (LPARAM)glb_pcGenres[iGenreIDX]); SendMessage(windows.wnd_playlist_IPEdit, CB_SETITEMDATA, (WPARAM)iNewItemIDX, (LPARAM)iGenreIDX); } } // Setup the initial string globals.m_iInPlaceSubItem = iSubItem; { switch (iSubItem) { case PLAYLIST_TITLE: SendMessage(windows.wnd_playlist_IPEdit, WM_SETTEXT, 0L, (LPARAM)CPLI_GetTrackName(hClickedItem)); if (!options.support_id3v2) SendMessage(windows.wnd_playlist_IPEdit, EM_LIMITTEXT, 30, 0); break; case PLAYLIST_ARTIST: SendMessage(windows.wnd_playlist_IPEdit, WM_SETTEXT, 0L, (LPARAM)CPLI_GetArtist(hClickedItem)); if (!options.support_id3v2) SendMessage(windows.wnd_playlist_IPEdit, EM_LIMITTEXT, 30, 0); break; case PLAYLIST_ALBUM: SendMessage(windows.wnd_playlist_IPEdit, WM_SETTEXT, 0L, (LPARAM)CPLI_GetAlbum(hClickedItem)); if (!options.support_id3v2) SendMessage(windows.wnd_playlist_IPEdit, EM_LIMITTEXT, 30, 0); break; case PLAYLIST_YEAR: SendMessage(windows.wnd_playlist_IPEdit, WM_SETTEXT, 0L, (LPARAM)CPLI_GetYear(hClickedItem)); if (!options.support_id3v2) SendMessage(windows.wnd_playlist_IPEdit, EM_LIMITTEXT, 4, 0); break; case PLAYLIST_TRACKNUM: { char cTrackNum[33]; unsigned char iTrackNum; iTrackNum = CPLI_GetTrackNum(hClickedItem); if (iTrackNum != CIC_INVALIDTRACKNUM && iTrackNum != 0) SendMessage(windows.wnd_playlist_IPEdit, WM_SETTEXT, 0L, (LPARAM)_itoa(iTrackNum, cTrackNum, 10)); } SendMessage(windows.wnd_playlist_IPEdit, EM_LIMITTEXT, 3, 0); break; case PLAYLIST_COMMENT: SendMessage(windows.wnd_playlist_IPEdit, WM_SETTEXT, 0L, (LPARAM)CPLI_GetComment(hClickedItem)); if (!options.support_id3v2) SendMessage(windows.wnd_playlist_IPEdit, EM_LIMITTEXT, 28, 0); break; case PLAYLIST_GENRE: SendMessage(windows.wnd_playlist_IPEdit, CB_SELECTSTRING, (WPARAM) - 1, (LPARAM)CPLI_GetGenre(hClickedItem)); break; } } globals.m_bIP_InhibitUpdates = FALSE; }
/** * name: ProfileList_BeginLabelEdit * desc: create an edit control to edit the label of the selected item * param: pList - handle to listview control's info structure * iItem - item index * iSubItem - subitem (column) index * return: handle to the edit control **/ static HWND ProfileList_BeginLabelEdit(LPLISTCTRL pList, INT iItem, INT iSubItem) { LVITEM lvi; LPLCITEM pItem; HANDLE hContact; RECT rcList; if (!PtrIsValid(pList)) return NULL; if (pList->labelEdit.hEdit) ProfileList_EndLabelEdit(pList, FALSE); lvi.mask = LVIF_PARAM|LVIF_STATE; lvi.stateMask = 0xFFFFFFFF; lvi.iItem = iItem; lvi.iSubItem = iSubItem; if (!ListView_GetItem(pList->hList, &lvi)) return NULL; pItem = (LPLCITEM)lvi.lParam; PSGetContact(GetParent(pList->hList), hContact); // do not edit deviders or protocol based contact information if (!(lvi.state & LVIS_SELECTED) || !PtrIsValid(pItem) || (hContact && (pItem->wFlags & CTRLF_HASPROTO))) return NULL; ListView_EnsureVisible(pList->hList, iItem, FALSE); ListView_GetSubItemRect(pList->hList, iItem, iSubItem, LVIR_BOUNDS, &pList->labelEdit.rcCombo); if (lvi.iSubItem == 0) { RECT rc2; ListView_GetSubItemRect(pList->hList, iItem, 1, LVIR_BOUNDS, &rc2); pList->labelEdit.rcCombo.right = rc2.left; } GetClientRect(pList->hList, &rcList); pList->labelEdit.rcCombo.right = min(pList->labelEdit.rcCombo.right, rcList.right); pList->labelEdit.rcCombo.left = max(pList->labelEdit.rcCombo.left, rcList.left); InflateRect(&pList->labelEdit.rcCombo, -1, -1); // create the button control for the combobox if (!iSubItem && pItem->idstrList) { pList->labelEdit.hBtn = CreateWindowEx(WS_EX_NOPARENTNOTIFY, UINFOBUTTONCLASS, NULL, WS_VISIBLE|WS_CHILD|MBS_DOWNARROW, pList->labelEdit.rcCombo.right - (pList->labelEdit.rcCombo.bottom - pList->labelEdit.rcCombo.top), pList->labelEdit.rcCombo.top, pList->labelEdit.rcCombo.bottom - pList->labelEdit.rcCombo.top, pList->labelEdit.rcCombo.bottom - pList->labelEdit.rcCombo.top, pList->hList, NULL, ghInst, NULL); if (pList->labelEdit.hBtn) { SetWindowLongPtr(pList->labelEdit.hBtn, GWLP_ID, BTN_EDIT); pList->labelEdit.rcCombo.right -= pList->labelEdit.rcCombo.bottom - pList->labelEdit.rcCombo.top; } } else { pList->labelEdit.rcCombo.bottom = 3 * pList->labelEdit.rcCombo.bottom - 2 * pList->labelEdit.rcCombo.top; if (rcList.bottom < pList->labelEdit.rcCombo.bottom) { OffsetRect(&pList->labelEdit.rcCombo, 0, rcList.bottom - pList->labelEdit.rcCombo.bottom - 2); } } // create the edit control pList->labelEdit.hEdit = CreateWindowEx(WS_EX_NOPARENTNOTIFY|WS_EX_CLIENTEDGE, _T("EDIT"), (!iSubItem && pItem->idstrList && pItem->iListItem > 0 && pItem->iListItem < pItem->idstrListCount) ? pItem->idstrList[pItem->iListItem].ptszTranslated : (iSubItem >= 0 && iSubItem < 2 && pItem->pszText[iSubItem] && *pItem->pszText[iSubItem]) ? pItem->pszText[iSubItem] : _T(""), WS_VISIBLE|WS_CHILD|(iSubItem ? (WS_VSCROLL|ES_MULTILINE|ES_AUTOVSCROLL) : ES_AUTOHSCROLL), pList->labelEdit.rcCombo.left, pList->labelEdit.rcCombo.top, pList->labelEdit.rcCombo.right - pList->labelEdit.rcCombo.left, pList->labelEdit.rcCombo.bottom - pList->labelEdit.rcCombo.top, pList->hList, NULL, ghInst, NULL); if (!pList->labelEdit.hEdit) return NULL; SendMessage(pList->labelEdit.hEdit, WM_SETFONT, (WPARAM)(pList->hFont), 0); SendMessage(pList->labelEdit.hEdit, EM_SETSEL, 0, (LPARAM)-1); SetUserData(pList->labelEdit.hEdit, pList); pList->labelEdit.dropDown.iItem = pItem->iListItem; pList->labelEdit.iItem = iItem; pList->labelEdit.iSubItem = iSubItem; pList->labelEdit.iTopIndex = ListView_GetTopIndex(pList->hList); pList->labelEdit.pItem = pItem; SetFocus(pList->labelEdit.hEdit); OldEditProc = (WNDPROC)SetWindowLongPtr(pList->labelEdit.hEdit, GWLP_WNDPROC, (LONG_PTR)ProfileList_LabelEditProc); return pList->labelEdit.hEdit; }
/* This function creates the out-basket window. */ BOOL FASTCALL CreateOutBasket( HWND hwnd ) { DWORD dwState; RECT rc; /* If outbasket window already open, bring it to the front * and display it. */ if( hwndOutBasket ) { Adm_MakeMDIWindowActive( hwndOutBasket ); return( TRUE ); } /* Register the out-basket window class if we have * not already done so. */ if( !fRegistered ) { WNDCLASS wc; wc.style = CS_HREDRAW | CS_VREDRAW; wc.lpfnWndProc = OutBasketWndProc; wc.hIcon = LoadIcon( hRscLib, MAKEINTRESOURCE(IDI_OUTBASKET) ); wc.hCursor = LoadCursor( NULL, IDC_ARROW ); wc.lpszMenuName = NULL; wc.cbWndExtra = MWE_EXTRA; wc.cbClsExtra = 0; wc.hbrBackground = NULL; wc.lpszClassName = szOutBaskWndClass; wc.hInstance = hInst; if( !RegisterClass( &wc ) ) return( FALSE ); fRegistered = TRUE; } /* The default position of the out-basket. */ GetClientRect( hwndMDIClient, &rc ); rc.left = rc.right / 3; InflateRect( &rc, -5, -5 ); dwState = 0; /* Load the out-basket bitmaps. */ hbmpOutBasket = LoadBitmap( hRscLib, MAKEINTRESOURCE(IDB_OUTBASKETBMPS) ); /* Get the actual window size, position and state. */ ReadProperWindowState( szOutBaskWndName, &rc, &dwState ); if( hwndActive && IsMaximized( hwndActive ) ) dwState = WS_MAXIMIZE; /* Create the window. */ hwndOutBasket = Adm_CreateMDIWindow( szOutBaskWndName, szOutBaskWndClass, hInst, &rc, dwState, 0L ); if( NULL == hwndOutBasket ) return( FALSE ); UpdateWindow( hwndOutBasket ); /* Set the initial focus. */ OutBasket_OnSetFocus( hwndOutBasket, NULL ); UpdateOutBasketStatus(); return( TRUE ); }
static void GB_draw(HTHEME theme, HWND hwnd, HDC hDC, ButtonState drawState, UINT dtFlags, BOOL focused) #endif { static const int states[] = { GBS_NORMAL, GBS_NORMAL, GBS_NORMAL, GBS_DISABLED, GBS_NORMAL }; RECT bgRect, textRect, contentRect; int state = states[ drawState ]; WCHAR *text = get_button_text(hwnd); LOGFONTW lf; HFONT font, hPrevFont = NULL; BOOL created_font = FALSE; #ifdef __REACTOS__ /* r74406 */ HWND parent; HBRUSH hBrush; RECT clientRect; #endif HRESULT hr = GetThemeFont(theme, hDC, BP_GROUPBOX, state, TMT_FONT, &lf); if (SUCCEEDED(hr)) { font = CreateFontIndirectW(&lf); if (!font) TRACE("Failed to create font\n"); else { hPrevFont = SelectObject(hDC, font); created_font = TRUE; } } else { #ifdef __REACTOS__ /* r73885 */ font = get_button_font(hwnd); #else font = (HFONT)SendMessageW(hwnd, WM_GETFONT, 0, 0); #endif hPrevFont = SelectObject(hDC, font); } GetClientRect(hwnd, &bgRect); textRect = bgRect; if (text) { SIZE textExtent; GetTextExtentPoint32W(hDC, text, lstrlenW(text), &textExtent); bgRect.top += (textExtent.cy / 2); textRect.left += 10; textRect.bottom = textRect.top + textExtent.cy; textRect.right = textRect.left + textExtent.cx + 4; ExcludeClipRect(hDC, textRect.left, textRect.top, textRect.right, textRect.bottom); } GetThemeBackgroundContentRect(theme, hDC, BP_GROUPBOX, state, &bgRect, &contentRect); ExcludeClipRect(hDC, contentRect.left, contentRect.top, contentRect.right, contentRect.bottom); #ifdef __REACTOS__ /* r73885 & r74149 */ if (prfFlag == 0) { if (IsThemeBackgroundPartiallyTransparent(theme, BP_GROUPBOX, state)) DrawThemeParentBackground(hwnd, hDC, NULL); } #else if (IsThemeBackgroundPartiallyTransparent(theme, BP_GROUPBOX, state)) DrawThemeParentBackground(hwnd, hDC, NULL); #endif #ifdef __REACTOS__ /* r74406 */ parent = GetParent(hwnd); if (!parent) parent = hwnd; hBrush = (HBRUSH)SendMessageW(parent, WM_CTLCOLORSTATIC, (WPARAM)hDC, (LPARAM)hwnd); if (!hBrush) /* did the app forget to call defwindowproc ? */ hBrush = (HBRUSH)DefWindowProcW(parent, WM_CTLCOLORSTATIC, (WPARAM)hDC, (LPARAM)hwnd ); GetClientRect(hwnd, &clientRect); FillRect( hDC, &clientRect, hBrush ); #endif DrawThemeBackground(theme, hDC, BP_GROUPBOX, state, &bgRect, NULL); SelectClipRgn(hDC, NULL); if (text) { InflateRect(&textRect, -2, 0); DrawThemeText(theme, hDC, BP_GROUPBOX, state, text, lstrlenW(text), 0, 0, &textRect); HeapFree(GetProcessHeap(), 0, text); } if (created_font) DeleteObject(font); if (hPrevFont) SelectObject(hDC, hPrevFont); }
int FindNCHit( PWND pwnd, LONG lPt) { POINT pt; RECT rcWindow; RECT rcClient; RECT rcClientAdj; int cBorders; int dxButton; pt.x = LOWORD(lPt); pt.y = HIWORD(lPt); if (!PtInRect(&pwnd->rcWindow, pt)) return HTNOWHERE; if (TestWF(pwnd, WFMINIMIZED)) { CopyInflateRect(&rcWindow, &pwnd->rcWindow, -(SYSMET(CXFIXEDFRAME) + SYSMET(CXBORDER)), -(SYSMET(CYFIXEDFRAME) + SYSMET(CYBORDER))); if (!PtInRect(&rcWindow, pt)) return HTCAPTION; goto CaptionHit; } // Get client rectangle rcClient = pwnd->rcClient; if (PtInRect(&rcClient, pt)) return HTCLIENT; // Are we in "pseudo" client, i.e. the client & scrollbars & border if (TestWF(pwnd, WEFCLIENTEDGE)) CopyInflateRect(&rcClientAdj, &rcClient, SYSMET(CXEDGE), SYSMET(CYEDGE)); else rcClientAdj = rcClient; if (TestWF(pwnd, WFVPRESENT)) rcClientAdj.right += SYSMET(CXVSCROLL); if (TestWF(pwnd, WFHPRESENT)) rcClientAdj.bottom += SYSMET(CYHSCROLL); if (!PtInRect(&rcClientAdj, pt)) { // Subtract out window borders cBorders = GetWindowBorders(pwnd->style, pwnd->ExStyle, TRUE, FALSE); CopyInflateRect(&rcWindow, &pwnd->rcWindow, -cBorders*SYSMET(CXBORDER), -cBorders*SYSMET(CYBORDER)); // Are we on the border? if (!PtInRect(&rcWindow, pt)) { // On a sizing border? if (!TestWF(pwnd, WFSIZEBOX)) { // // Old compatibility thing: For 3.x windows that just had // a border, we returned HTNOWHERE, believe it or not, // because our hit-testing code was so brain dead. // if (!TestWF(pwnd, WFWIN40COMPAT) && !TestWF(pwnd, WFDLGFRAME) && !TestWF(pwnd, WEFDLGMODALFRAME)) { return(HTNOWHERE); } else { return(HTBORDER); // We are on a dlg frame. } } else { int ht; // // Note this improvement. The HT codes are numbered so that // if you subtract HTSIZEFIRST-1 from them all, they sum up. I.E., // (HTLEFT - HTSIZEFIRST + 1) + (HTTOP - HTSIZEFIRST + 1) == // (HTTOPLEFT - HTSIZEFIRST + 1). // if (TestWF(pwnd, WEFTOOLWINDOW)) InflateRect(&rcWindow, -SYSMET(CXSMSIZE), -SYSMET(CYSMSIZE)); else InflateRect(&rcWindow, -SYSMET(CXSIZE), -SYSMET(CYSIZE)); if (pt.y < rcWindow.top) ht = (HTTOP - HTSIZEFIRST + 1); else if (pt.y >= rcWindow.bottom) ht = (HTBOTTOM - HTSIZEFIRST + 1); else ht = 0; if (pt.x < rcWindow.left) ht += (HTLEFT - HTSIZEFIRST + 1); else if (pt.x >= rcWindow.right) ht += (HTRIGHT - HTSIZEFIRST + 1); return (ht + HTSIZEFIRST - 1); } } // Are we above the client area? if (pt.y < rcClientAdj.top) { // Are we in the caption? if (TestWF(pwnd, WFBORDERMASK) == LOBYTE(WFCAPTION)) { CaptionHit: if (pt.y >= rcWindow.top) { if (TestWF(pwnd, WEFTOOLWINDOW)) { rcWindow.top += SYSMET(CYSMCAPTION); dxButton = SYSMET(CXSMSIZE); } else { rcWindow.top += SYSMET(CYCAPTION); dxButton = SYSMET(CXSIZE); } if ((pt.y >= rcWindow.top) && TestWF(pwnd, WFMPRESENT)) return(HTMENU); if ((pt.x >= rcWindow.left) && (pt.x < rcWindow.right) && (pt.y < rcWindow.top)) { // Are we in the window menu? if (TestWF(pwnd, WFSYSMENU)) { rcWindow.left += dxButton; if (pt.x < rcWindow.left) { if (!_HasCaptionIcon(pwnd)) // iconless windows have no sysmenu hit rect return(HTCAPTION); return(HTSYSMENU); } } else if (TestWF(pwnd, WFWIN40COMPAT)) return(HTCAPTION); // only a close button if window has a system menu // Are we in the close button? rcWindow.right -= dxButton; if (pt.x >= rcWindow.right) return HTCLOSE; if ((pt.x < rcWindow.right) && !TestWF(pwnd, WEFTOOLWINDOW)) { // Are we in the maximize/restore button? if (TestWF(pwnd, (WFMAXBOX | WFMINBOX))) { // Note that sizing buttons are same width for both // big captions and small captions. rcWindow.right -= dxButton; if (pt.x >= rcWindow.right) return HTZOOM; // Are we in the minimize button? rcWindow.right -= dxButton; if (pt.x >= rcWindow.right) return HTREDUCE; } else if (TestWF(pwnd, WEFCONTEXTHELP)) { rcWindow.right -= dxButton; if (pt.x >= rcWindow.right) return HTHELP; } } } } // We're in the caption proper return HTCAPTION; } // // Are we in the menu? // if (TestWF(pwnd, WFMPRESENT)) return HTMENU; } } else { // // NOTE: // We can only be here if we are on the client edge, horz scroll, // sizebox, or vert scroll. Hence, if we are not on the first 3, // we must be on the last one. // // // Are we on the client edge? // if (TestWF(pwnd, WEFCLIENTEDGE)) { InflateRect(&rcClientAdj, -SYSMET(CXEDGE), -SYSMET(CYEDGE)); if (!PtInRect(&rcClientAdj, pt)) return(HTBORDER); } // // Are we on the scrollbars? // if (TestWF(pwnd, WFHPRESENT) && (pt.y >= rcClient.bottom)) { UserAssert(pt.y < rcClientAdj.bottom); if (TestWF(pwnd, WFVPRESENT) && (pt.x >= rcClient.right)) return(SizeBoxHwnd(pwnd) ? HTBOTTOMRIGHT : HTGROWBOX); else return(HTHSCROLL); } else { UserAssert(TestWF(pwnd, WFVPRESENT)); UserAssert(pt.x >= rcClient.right); UserAssert(pt.x < rcClientAdj.right); return(HTVSCROLL); } } // // We give up. // // Win31 returned HTNOWHERE in this case; For compatibility, we will // keep it that way. // return(HTNOWHERE); }
STDMETHODIMP CDrawTxt::GetBoundingRect(RECT* pBoundingRect) { USES_CONVERSION; RECT rcCaption; RECTFToRECT(&m_rcPosition, &rcCaption); // 矫正斜体出界的情况, 计算10次大概耗时1毫秒 /* if (m_bItalic) { //创建设备上下文 HDC hDC = CreateDC(_T("DISPLAY"), NULL, NULL, NULL); HFONT hFont = CreateTextFont(ROUND(m_dFontHeight), ROUND(m_dFontWidth)); HFONT hOldFont = (HFONT)SelectObject(hDC, hFont); LPTSTR szCaption = W2T(m_bstrCaption); int cbCaption = lstrlen(szCaption); UINT uFormat = DT_NOCLIP|DT_CALCRECT|DT_NOPREFIX; if (m_nTextAlign == TextAlignCenter) uFormat |= DT_CENTER; else if (m_nTextAlign == TextAlignRight) uFormat |= DT_RIGHT; else uFormat |= DT_LEFT; int nLeftMargin = 0; int nRightMargine = 0; OLECHAR* pChar = m_bstrCaption; OLECHAR* pLineShartChar = pChar; if (pChar != NULL && *pChar != 0) { int nMaxLineWidth = 0; while (1) { // 如果是换行符 if (*pChar == 13 || *pChar == 10 || *pChar == 0) { if (pChar > pLineShartChar) { RECT rcT = rcCaption; CComBSTR bstrT(pChar - pLineShartChar, pLineShartChar); DrawText(hDC, OLE2T(bstrT), -1, &rcT, uFormat); ABCFLOAT abcfloat; GetCharABCWidthsFloatW(hDC, *pLineShartChar, *pLineShartChar, &abcfloat); int A = ROUND(abcfloat.abcfA); GetCharABCWidthsFloatW(hDC, *(pChar - 1), *(pChar - 1), &abcfloat); int C = ROUND(abcfloat.abcfC); if (A < 0) rcT.left += A; if (C < 0) rcT.right -= C; // two minus' make a plus if (nLeftMargin < rcCaption.left - rcT.left) nLeftMargin = rcCaption.left - rcT.left; if (nRightMargine < rcT.right - rcCaption.right) nRightMargine = rcT.right - rcCaption.right; } if (*pChar == 0) break; if (*(pChar + 1) == 10 || *(pChar + 1) == 13) pChar++; pChar++; pLineShartChar = pChar; } else { pChar++; } } } SelectObject(hDC, hOldFont); DeleteObject(hFont); DeleteDC(hDC); rcCaption.left -= nLeftMargin; rcCaption.right += nRightMargine; }*/ int nDX = ROUND(m_dFontWidth); if (nDX == 0) nDX = ROUND(m_dFontHeight); InflateRect(&rcCaption, nDX, 1); *pBoundingRect = rcCaption; return S_OK; }
void CEditView::ScrollTo( int nCol, int nRow, BOOL bSmooth ) { if ( nCol != m_nLeftIndex ) { int cxShift = ( m_nLeftIndex - nCol ) * m_cxChar; SetRightIndex( nCol + m_nRightIndex - m_nLeftIndex ); m_nLeftIndex = nCol; if ( !m_pCtrl->DelayPaint() ) { RECT rcClip = m_rcView; rcClip.left += GetLeftMargin( TRUE, TRUE ); if ( bSmooth && m_pCtrl->SmoothScrolling() ) { int nSign = ( cxShift < 0 ) ? -1 : +1; int nScrollBy = cxShift / 6; if ( !nScrollBy ) { // small font used! nScrollBy = 1; } int cx = 0; do { if ( nSign * ( nScrollBy + cx ) > nSign * cxShift ) { nScrollBy = cxShift - cx; } cx += nScrollBy; RECT rcInval; VERIFY( ScrollWindowEx( m_hWndView, nScrollBy, 0, NULL, &rcClip, NULL, &rcInval, 0 ) ); // factor in a bit of extra space in case a DBCS char is only half-painted InflateRect( &rcInval, m_cxChar, 0 ); InvalidateRect( m_hWndView, &rcInval, FALSE ); } while ( nSign * cx < nSign * cxShift ); ASSERT( cx == cxShift ); } else { RECT rcInval; VERIFY( ScrollWindowEx( m_hWndView, cxShift, 0, NULL, &rcClip, NULL, &rcInval, 0 ) ); // factor in a bit of extra space in case a DBCS char is only half-painted InflateRect( &rcInval, m_cxChar, 0 ); InvalidateRect( m_hWndView, &rcInval, FALSE ); } m_pCtrl->SafeUpdateWindow(); } else { m_pCtrl->Repaint( FALSE ); } if ( m_hWndHScroll ) { SCROLLINFO si; si.cbSize = sizeof( SCROLLINFO ); si.fMask = SIF_POS; si.nPos = m_nLeftIndex; SendMessage( m_hWndHScroll, SBM_SETSCROLLINFO, TRUE, ( LPARAM )&si ); } } if ( nRow != m_nTopIndex ) { int cyShift = ( m_nTopIndex - nRow ) * m_cyLine; SetBottomIndex( nRow + m_nBottomIndex - m_nTopIndex ); m_nTopIndex = nRow; if ( !m_pCtrl->DelayPaint() ) { if ( bSmooth && m_pCtrl->SmoothScrolling() ) { int nSign = ( cyShift < 0 ) ? -1 : +1; int nScrollBy = cyShift / 6; if ( !nScrollBy ) { // small font used! nScrollBy = 1; } int cy = 0; do { if ( nSign * ( nScrollBy + cy ) > nSign * cyShift ) { nScrollBy = cyShift - cy; } cy += nScrollBy; VERIFY( ScrollWindowEx( m_hWndView, 0, nScrollBy, NULL, &m_rcView, NULL, NULL, SW_INVALIDATE ) ); } while ( nSign * cy < nSign * cyShift ); ASSERT( cy == cyShift ); } else { VERIFY( ScrollWindowEx( m_hWndView, 0, cyShift, NULL, &m_rcView, NULL, NULL, SW_INVALIDATE ) ); } m_pCtrl->SafeUpdateWindow(); } else { m_pCtrl->Repaint( FALSE ); } if ( m_hWndVScroll ) { SCROLLINFO si; si.cbSize = sizeof( SCROLLINFO ); si.fMask = SIF_POS; si.nPos = m_nTopIndex; SendMessage( m_hWndVScroll, SBM_SETSCROLLINFO, TRUE, ( LPARAM )&si ); } } }
void Headr_OnDrawItem ( HWND hWnd, HDC hDC, HEADERDATA* pthis, int iItem, PHEADERITEM pItm ) { RECT rcDraw; HFONT hOFont; HPEN hOPen; UINT fmt; HPEN hGPen = CreatePen ( PS_SOLID, 1, GetSysColor ( COLOR_BTNSHADOW ) ); HPEN hWPen = GetStockObject ( WHITE_PEN ); CopyRect ( &rcDraw, &pItm->rc ); FillRect ( hDC, &rcDraw, GetStockObject ( LTGRAY_BRUSH ) ); InflateRect ( &rcDraw, -HDMETRIC_CYBORDER, -2 ); if ( pthis->eMouse == eItemClk ) OffsetRect ( &rcDraw, 1, 1 ); fmt = DT_VCENTER; fmt |= ( pItm->data.fmt & HDF_CENTER )? DT_CENTER : ( pItm->data.fmt & HDF_RIGHT )? DT_RIGHT : DT_LEFT; if ( ( pItm->data.fmt & HDF_STRING ) && pItm->text ) { hOFont = SelectObject ( hDC, pthis->hFont ); SetBkMode ( hDC, TRANSPARENT ); Headr_IDrawFittedString ( hDC, pItm->text, fmt, &rcDraw ); SelectObject ( hDC, hOFont ); } else if ( ( pItm->data.fmt & HDF_BITMAP ) && pItm->data.hbm ) Headr_IDrawBitmap ( hDC, pItm->data.hbm, fmt, &rcDraw ); else if ( pItm->data.fmt & HDF_OWNERDRAW ) { Headr_IOwnerDraw ( hWnd, hDC, pthis, iItem, pItm ); goto EndDrawItem; } if ( pthis->eMouse == eItemClk ) { hOPen = SelectObject ( hDC, hGPen ); MoveToEx ( hDC, pItm->rc.left, pItm->rc.bottom, ( LPPOINT )NULL ); LineTo ( hDC, pItm->rc.left, pItm->rc.top ); LineTo ( hDC, pItm->rc.right, pItm->rc.top ); SelectObject ( hDC, hWPen ); LineTo ( hDC, pItm->rc.right, pItm->rc.bottom ); LineTo ( hDC, pItm->rc.left, pItm->rc.bottom ); SelectObject ( hDC, hOPen ); } else { hOPen = SelectObject ( hDC, hGPen ); MoveToEx ( hDC, pItm->rc.right, pItm->rc.top, ( LPPOINT )NULL ); LineTo ( hDC, pItm->rc.right, pItm->rc.bottom ); LineTo ( hDC, pItm->rc.left, pItm->rc.bottom ); if ( pthis->uStyles & HDS_BUTTONS ) { MoveToEx ( hDC, pItm->rc.right-1, pItm->rc.top+1, ( LPPOINT )NULL ); LineTo ( hDC, pItm->rc.right-1, pItm->rc.bottom-1 ); LineTo ( hDC, pItm->rc.left, pItm->rc.bottom-1 ); SelectObject ( hDC, hWPen ); } LineTo ( hDC, pItm->rc.left, pItm->rc.top ); LineTo ( hDC, pItm->rc.right, pItm->rc.top ); SelectObject ( hDC, hOPen ); } EndDrawItem: DeleteObject ( hGPen ); }
bool playlist_view::draw_items(HDC dc, int start_item, int count) { // profiler(draw_items); if (!drawing_enabled) return false; static_api_ptr_t<playlist_manager> playlist_api; HDC hdc_mem = 0; RECT rect, item, item_area, bk, draw/*,text*/; GetClientRect(wnd_playlist, &rect); rect.top += get_header_height(); int item_height = get_item_height(); HBRUSH br = 0; HBITMAP hbm_mem = 0, hbm_old = 0; pfc::array_t<int, pfc::alloc_fast_aggressive> widths; int total_width = get_column_widths(widths); int t = columns.get_count(); const bit_array & p_mask = g_cache.active_get_columns_mask(); item_area.left = rect.left; item_area.right = rect.right; item_area.top = rect.top + (item_height*start_item); item_area.bottom = item_area.top + (item_height*count); item.left = 0 - horizontal_offset; item.right = item.left + total_width; item.top = 0; item.bottom = item.top + item_height; bk.top = 0; bk.left = 0; bk.bottom = item_height*count; bk.right = rect.right - rect.left; /*static */pfc::string8_fast_aggressive temp; temp.prealloc(512); /* edit01 */ hdc_mem = CreateCompatibleDC(dc); COLORREF colourfore = 0xff; hbm_mem = CreateCompatibleBitmap(dc, rect.right - rect.left, item_height*count); hbm_old = (HBITMAP)SelectObject(hdc_mem, hbm_mem); HGDIOBJ font_old = SelectObject(hdc_mem, g_font); cui::colours::helper p_helper(appearance_client_pv_impl::g_guid); //fill entire area with back colour br = CreateSolidBrush(p_helper.get_colour(cui::colours::colour_background)); FillRect(hdc_mem, &bk, br); DeleteObject(br); //need checks here because of filling background { int total = playlist_api->activeplaylist_get_item_count(); if (start_item + count + scroll_item_offset > total) //end item is NOT inclusive { count -= (start_item + count + scroll_item_offset) - total; } } int end_item = start_item + count; //draw each item int n, focus = playlist_api->activeplaylist_get_focus_item(); // static int pcount; t_size playing_index, playing_playlist; playlist_api->get_playing_item_location(&playing_playlist, &playing_index); bool b_playback = static_api_ptr_t<play_control>()->is_playing(); if (g_cache.get_active_playlist() != playing_playlist) playing_index = pfc_infinite; for (n = start_item; n < end_item; n++) { bool sel = playlist_api->activeplaylist_is_item_selected(n + scroll_item_offset); bool b_focused = GetFocus() == wnd_playlist || IsChild(wnd_playlist, GetFocus()); bool b_playing = b_playback && playing_index == (n + scroll_item_offset); //draw each column of each item int theme_state = NULL; if (sel) theme_state = (b_playing ? LISS_HOTSELECTED : (b_focused ? LISS_SELECTED : LISS_SELECTEDNOTFOCUS)); else if (b_playing) theme_state = LISS_HOT; bool b_themed = m_theme && p_helper.get_themed() && IsThemePartDefined(m_theme, LVP_LISTITEM, theme_state); if (b_themed && theme_state) { if (IsThemeBackgroundPartiallyTransparent(m_theme, LVP_LISTITEM, theme_state)) DrawThemeParentBackground(get_wnd(), hdc_mem, &item); DrawThemeBackground(m_theme, hdc_mem, LVP_LISTITEM, theme_state, &item, NULL); } //int total = playlist_api->activeplaylist_get_item_count(); int c, offset = 0, i = 0; for (c = 0; c < t; c++) { if (p_mask[c]) { draw.left = item.left + offset; draw.top = item.top; offset += widths[i]; draw.right = item.left + offset; draw.bottom = item.bottom; { // profiler_debug(draw_item_get_string); g_cache.active_get_display_name(n + scroll_item_offset, i, temp); } colourinfo colours(0x000000, 0x000000, 0xFF, 0xFF, 0, 0xFF); g_cache.active_get_colour(n + scroll_item_offset, i, colours); if (b_themed) { //COLORREF cr_back= get_default_colour(colours::COLOUR_BACK); //colourfore = get_default_colour(colours::COLOUR_TEXT); //GetThemeColor(m_theme, LVP_LISTITEM, sel ? (GetFocus() == wnd_playlist ? LIS_SELECTED : LIS_SELECTEDNOTFOCUS) : LIS_NORMAL, TMT_WINDOWTEXT, &colourfore); colourfore = GetThemeSysColor(m_theme, sel ? COLOR_BTNTEXT : COLOR_WINDOWTEXT); //GetThemeColor(m_theme, LVP_LISTITEM, sel ? (GetFocus() == wnd_playlist ? LIS_SELECTED : LIS_SELECTEDNOTFOCUS) : LIS_NORMAL, TMT_TEXTCOLOR, &colourfore); if (!theme_state) { //GetThemeColor(m_theme, LVP_LISTITEM, LIS_NORMAL, TMT_FILLCOLOR, &colourfore); br = CreateSolidBrush(colours.background_colour); FillRect(hdc_mem, &draw, br); } } else { if (sel) { /* TEST */ if (GetFocus() == wnd_playlist) { colourfore = colours.selected_text_colour; br = CreateSolidBrush(colours.selected_background_colour); } else { colourfore = colours.selected_text_colour_non_focus; br = CreateSolidBrush(colours.selected_background_colour_non_focus); } } else { colourfore = colours.text_colour; br = CreateSolidBrush(colours.background_colour); } //draw cell background //if (!b_themed) FillRect(hdc_mem, &draw, br); } if (br) { DeleteObject(br); br = 0; } //render text //if (b_themed) // DrawThemeText(m_theme, hdc_mem, LVP_LISTITEM, sel ? (GetFocus() == wnd_playlist ? LIS_SELECTED : LIS_SELECTEDNOTFOCUS) : LIS_NORMAL, L"test", 4, 0, 0, &draw); //else ui_helpers::text_out_colours_tab(hdc_mem, temp, temp.length(), 2, 1, &draw, sel, colourfore, TRUE, true, (cfg_ellipsis != 0), (ui_helpers::alignment)columns[c]->align); if (colours.use_frame_left) { HPEN pen = CreatePen(PS_SOLID, 1, colours.frame_left); HPEN pen_old = (HPEN)SelectObject(hdc_mem, pen); MoveToEx(hdc_mem, draw.left, draw.top, 0); LineTo(hdc_mem, draw.left, draw.bottom); SelectObject(hdc_mem, pen_old); DeleteObject(pen); } if (colours.use_frame_top) { HPEN pen = CreatePen(PS_SOLID, 1, colours.frame_top); HPEN pen_old = (HPEN)SelectObject(hdc_mem, pen); MoveToEx(hdc_mem, draw.left, draw.top, 0); LineTo(hdc_mem, draw.right, draw.top); SelectObject(hdc_mem, pen_old); DeleteObject(pen); } if (colours.use_frame_right) { HPEN pen = CreatePen(PS_SOLID, 1, colours.frame_right); HPEN pen_old = (HPEN)SelectObject(hdc_mem, pen); MoveToEx(hdc_mem, draw.right - 1, draw.top, 0); LineTo(hdc_mem, draw.right - 1, draw.bottom); SelectObject(hdc_mem, pen_old); DeleteObject(pen); } if (colours.use_frame_bottom) { HPEN pen = CreatePen(PS_SOLID, 1, colours.frame_bottom); HPEN pen_old = (HPEN)SelectObject(hdc_mem, pen); MoveToEx(hdc_mem, draw.right - 1, draw.bottom - 1, 0); LineTo(hdc_mem, draw.left - 1, draw.bottom - 1); SelectObject(hdc_mem, pen_old); DeleteObject(pen); } i++; } } //draw focus frame if ((n + scroll_item_offset) == focus) { if (m_always_show_focus || (!(SendMessage(get_wnd(), WM_QUERYUISTATE, NULL, NULL) & UISF_HIDEFOCUS) && b_focused)) { RECT rc_focus = item; if (m_theme && p_helper.get_themed() && IsThemePartDefined(m_theme, LVP_LISTITEM, LISS_SELECTED)) InflateRect(&rc_focus, -1, -1); if (!p_helper.get_bool(cui::colours::bool_use_custom_active_item_frame)) { DrawFocusRect(hdc_mem, &rc_focus); } else { br = CreateSolidBrush(p_helper.get_colour(cui::colours::colour_active_item_frame)); FrameRect(hdc_mem, &rc_focus, br); DeleteObject(br); } } } item.top += item_height; item.bottom += item_height; } BitBlt(dc, item_area.left, item_area.top, item_area.right - item_area.left, item_area.bottom - item_area.top, hdc_mem, 0, 0, SRCCOPY); if (font_old) SelectObject(hdc_mem, font_old); SelectObject(hdc_mem, hbm_old); DeleteObject(hbm_mem); DeleteDC(hdc_mem); return true; }
BOOL Status( HWND hWnd, LPSTR lpString ) /***********************************************************************/ { static HBITMAP hBubble,hMask,hSaveBits; BOOL bBubble = FALSE; if (hWnd == (HWND)-1) { // remove bubble from screen, then clean up Status (0,NULL); if (hBubble) { DeleteObject (hBubble); hBubble = 0; } if (hMask) { DeleteObject (hMask); hMask = 0; } if (hSaveBits) { DeleteObject (hSaveBits); hSaveBits = 0; } } else { static char szPrevString[256]; static RECT rBubble,rText; static POINT ptBubble,ptLimit; HBITMAP hBitmap; HDC hDC,hMemDC; hDC = GetDC (HWND_DESKTOP); if (lpString && *lpString) { if (!hBubble) { BITMAP bmBubble; // load bubble bitmap hBubble = DibResource2Bitmap (hInstAstral,IDC_STATUSBUBBLE); GetObject (hBubble,sizeof bmBubble,(LPVOID)&bmBubble); // get bubble rect rBubble.left = 0; rBubble.right = bmBubble.bmWidth; rBubble.top = 0; rBubble.bottom = bmBubble.bmHeight; // get text rect rText = rBubble; InflateRect (&rText,-50,-50); OffsetRect (&rText,8,0); // get screen limits ptLimit.x = ptLimit.y = 0; MapWindowPoints (AstralDlgGet (IDD_MAIN),HWND_DESKTOP, &ptLimit,1); ptLimit.x += 640; ptLimit.y += 480; } if (hBubble) { if (!hSaveBits) { #define XFUDGE 40 #define YFUDGE 20 // get bubble position GetCursorPos (&ptBubble); if ((ptBubble.x + rBubble.right + XFUDGE) > ptLimit.x) ptBubble.x -= rBubble.right + XFUDGE; else ptBubble.x += XFUDGE; if ((ptBubble.y + rBubble.bottom + YFUDGE) > ptLimit.y) ptBubble.y -= rBubble.bottom + YFUDGE; else ptBubble.y += YFUDGE; // save background hMemDC = CreateCompatibleDC (hDC); hSaveBits = CreateCompatibleBitmap (hDC, rBubble.right,rBubble.bottom); hBitmap = (HBITMAP)SelectObject (hMemDC,hSaveBits); BitBlt (hMemDC,0,0,rBubble.right,rBubble.bottom, hDC,ptBubble.x,ptBubble.y,SRCCOPY); SelectObject (hMemDC,hBitmap); DeleteDC (hMemDC); } if (!*szPrevString || lstrcmp (lpString,szPrevString) != 0) { HBITMAP hTemp; RECT rTemp; // draw bubble on screen hTemp = DrawTransDIB (hDC,hBubble,hMask, ptBubble.x + rBubble.right / 2, ptBubble.y + rBubble.bottom / 2); if (!hMask) hMask = hTemp; // draw text in bubble rTemp = rText; OffsetRect (&rTemp,ptBubble.x,ptBubble.y); DrawText (hDC,lpString,-1,&rTemp,DT_CENTER | DT_WORDBREAK); lstrcpy (szPrevString,lpString); // indicate that bubble was actually drawn, not skipped bBubble = TRUE; } } } else { if (hSaveBits) { // Restore background hMemDC = CreateCompatibleDC (hDC); hBitmap = (HBITMAP)SelectObject (hMemDC,hSaveBits); BitBlt (hDC,ptBubble.x,ptBubble.y, rBubble.right,rBubble.bottom,hMemDC,0,0,SRCCOPY); SelectObject (hMemDC,hBitmap); DeleteObject (hSaveBits); DeleteDC (hMemDC); hSaveBits = 0; } *szPrevString = 0; } ReleaseDC (HWND_DESKTOP,hDC); } return bBubble; }
LRESULT __stdcall PlayerPanel::PlayerButtonProc(HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam) { switch (Msg) { case WM_LBUTTONDOWN: { SetCapture(hWnd); /* Show menu */ if (GetWindowLong(hWnd, GWL_USERDATA) < 2) { RECT R; GetWindowRect(hWnd, &R); PostMessage(GetParent(hWnd), WM_CONTEXTMENU, (WPARAM)hWnd, MAKELPARAM(R.left,R.bottom)); } /* Set button status to pressed */ SetWindowLong(hWnd, GWL_USERDATA, 2); InvalidateRect(hWnd, NULL, TRUE); return 0; } case WM_LBUTTONUP: { ReleaseCapture(); /* Set button status to hover */ SetWindowLong(hWnd, GWL_USERDATA, 1); InvalidateRect(hWnd, NULL, TRUE); return 0; } case WM_MOUSEMOVE: { /* Track mouse leave */ TRACKMOUSEEVENT* Event = new TRACKMOUSEEVENT; Event->cbSize = sizeof(TRACKMOUSEEVENT); Event->dwFlags = TME_LEAVE; Event->hwndTrack = hWnd; TrackMouseEvent(Event); /* Set button status to hover */ SetWindowLong(hWnd, GWL_USERDATA, 1); InvalidateRect(hWnd, NULL, TRUE); return 0; } case WM_MOUSELEAVE: { if (GetWindowLong(hWnd, GWL_USERDATA) < 2) { /* Set button status to none */ SetWindowLong(hWnd, GWL_USERDATA, 0); InvalidateRect(hWnd, NULL, TRUE); } return 0; } case WM_PAINT: { PlayerPanel* Panel = (PlayerPanel*)GetWindowLong(GetParent(hWnd), GWL_USERDATA); if (Panel != NULL) { PAINTSTRUCT PS; HDC DC = BeginPaint(hWnd, &PS); if (DC != NULL) { RECT R; GetClientRect(hWnd, &R); /* Paint the background */ if (GetWindowLong(hWnd, GWL_USERDATA) == 0) { /* Plain background */ HBRUSH OldBrush = (HBRUSH)SelectObject(DC,CreateSolidBrush(GetSysColor(Panel->Game != NULL && Panel->Game->GetActivePlayer() == Panel->Color && Panel->Game->GetState() != Undefined ? COLOR_HIGHLIGHT : COLOR_BTNFACE))); HPEN OldPen = (HPEN)SelectObject(DC,CreatePen(PS_SOLID,1,GetSysColor(Panel->Game != NULL && Panel->Game->GetActivePlayer() == Panel->Color && Panel->Game->GetState() != Undefined ? COLOR_HIGHLIGHT : COLOR_BTNFACE))); Rectangle(DC,R.top,R.left,R.right-R.left,R.bottom-R.top); DeleteObject(SelectObject(DC,OldPen)); DeleteObject(SelectObject(DC,OldBrush)); } else { /* Button frame background */ DRAWITEMSTRUCT* Item = new DRAWITEMSTRUCT; Item->hDC = DC; Item->itemState = (GetWindowLong(hWnd, GWL_USERDATA) > 1 ? ODS_SELECTED : ODS_DEFAULT); Item->rcItem = R; DrawCustomButton(hWnd, Item); delete Item; } /* Draw the player's name */ if (Panel->Game != NULL) { InflateRect(&R,-5,-1); const ChessPlayer* Player = Panel->Game->GetPlayer(Panel->Color); SetBkMode(DC,TRANSPARENT); SetTextColor(DC, GetSysColor(Panel->Game->GetActivePlayer() == Panel->Color && Panel->Game->GetState() != Undefined && GetWindowLong(hWnd, GWL_USERDATA) == 0 ? COLOR_HIGHLIGHTTEXT : COLOR_BTNTEXT)); HFONT OldFont = (HFONT)SelectObject(DC,EasyCreateFont(DC,DefaultSystemFont,9,0)); const char* Text = Player->Name.c_str(); if (strlen(Text) == 0) { if (Panel->Color == White) Text = "White"; else Text = "Black"; } DrawText(DC,Text,strlen(Text),&R,DT_NOPREFIX|DT_SINGLELINE|DT_LEFT|DT_VCENTER|DT_END_ELLIPSIS); DeleteObject(SelectObject(DC,OldFont)); } } EndPaint(hWnd, &PS); } return 0; } } return CallWindowProc(OldPlayerButtonProc, hWnd, Msg, wParam, lParam); }
static VOID WinPrev_OnDraw( IN HDC hDC, IN PWINPREV_DATA pData) { PCONSOLE_STATE_INFO pConInfo = (PCONSOLE_STATE_INFO)pData->pData; HBRUSH hBrush; RECT rcWin, fRect; SIZE /*siBorder,*/ siFrame, siButton, siScroll; SIZE resize; RECT rcItem; GetClientRect(pData->hWnd, &rcItem); /* * Retrieve some system metrics and rescale them. * They will be added separately, so that to always round the sizes up. */ /* Don't care about border as it is almost always 1 and <= frame size */ /* Example: Frame = 4, or 13 ... while Border = 1 */ // siBorder.cx = GetSystemMetrics(SM_CXBORDER); // siBorder.cy = GetSystemMetrics(SM_CYBORDER); /* Window frame size */ siFrame.cx = GetSystemMetrics(SM_CXFRAME); if (siFrame.cx > 0) { siFrame.cx = RescaleCX(pData, siFrame.cx); siFrame.cx = max(1, siFrame.cx); } siFrame.cy = GetSystemMetrics(SM_CYFRAME); if (siFrame.cy > 0) { siFrame.cy = RescaleCY(pData, siFrame.cy); siFrame.cy = max(1, siFrame.cy); } /* Window caption buttons */ siButton.cx = GetSystemMetrics(SM_CXSIZE); siButton.cx = RescaleCX(pData, siButton.cx); siButton.cx = max(1, siButton.cx); siButton.cy = GetSystemMetrics(SM_CYSIZE); siButton.cy = RescaleCY(pData, siButton.cy); siButton.cy = max(1, siButton.cy); /* Enlarge them for improving their appearance */ // siButton.cx *= 2; siButton.cy *= 2; /* Dimensions of the scrollbars */ siScroll.cx = GetSystemMetrics(SM_CXVSCROLL); siScroll.cx = RescaleCX(pData, siScroll.cx); siScroll.cx = max(1, siScroll.cx); siScroll.cy = GetSystemMetrics(SM_CYHSCROLL); siScroll.cy = RescaleCY(pData, siScroll.cy); siScroll.cy = max(1, siScroll.cy); // FIXME: Use SM_CXMIN, SM_CYMIN ?? /* * Compute the console window layout */ /* We start with the console client area, rescaled for the preview */ SetRect(&rcWin, 0, 0, pConInfo->WindowSize.X * pConInfo->FontSize.X, pConInfo->WindowSize.Y * pConInfo->FontSize.Y); RescaleRect(pData, rcWin); /* Add the scrollbars if needed (does not account for any frame) */ if (pConInfo->WindowSize.X < pConInfo->ScreenBufferSize.X) { /* Horizontal scrollbar */ rcWin.bottom += siScroll.cy; // NOTE: If an additional exterior frame is needed, add +1 } else { /* No scrollbar */ siScroll.cy = 0; } if (pConInfo->WindowSize.Y < pConInfo->ScreenBufferSize.Y) { /* Vertical scrollbar */ rcWin.right += siScroll.cx; // NOTE: If an additional exterior frame is needed, add +1 } else { /* No scrollbar */ siScroll.cx = 0; } /* Add the title bar, taking into account the frames */ rcWin.top -= siButton.cy - 1; /* If we have a non-zero window frame size, add an interior border and the frame */ resize.cx = (siFrame.cx > 0 ? 1 + siFrame.cx : 0); resize.cy = (siFrame.cy > 0 ? 1 + siFrame.cy : 0); /* Add the outer border */ ++resize.cx, ++resize.cy; InflateRect(&rcWin, resize.cx, resize.cy); /* Finally, move the window rectangle back to its correct origin */ OffsetRect(&rcWin, -rcWin.left, -rcWin.top); if ( pConInfo->WindowPosition.x == MAXDWORD && pConInfo->WindowPosition.y == MAXDWORD ) { // OffsetRect(&rcWin, (rcItem.right - rcItem.left) / 3, (rcItem.bottom - rcItem.top) / 3); OffsetRect(&rcWin, 0, 0); } else { OffsetRect(&rcWin, RescaleCX(pData, pConInfo->WindowPosition.x), RescaleCY(pData, pConInfo->WindowPosition.y)); } /* * Paint the preview window */ /* Fill the background with desktop colour */ FillRect(hDC, &rcItem, GetSysColorBrush(COLOR_BACKGROUND)); /* * Draw the exterior frame. Use 'FillRect' instead of 'FrameRect' * so that, when we want to draw frames around other elements, * we can just instead separate them with space instead of redrawing * a frame with 'FrameRect'. */ FillRect(hDC, &rcWin, GetSysColorBrush(COLOR_WINDOWFRAME)); InflateRect(&rcWin, -1, -1); /* Draw the border */ hBrush = GetSysColorBrush(COLOR_ACTIVEBORDER); if (siFrame.cx > 0) { SetRect(&fRect, rcWin.left, rcWin.top, rcWin.left + siFrame.cx, rcWin.bottom); FillRect(hDC, &fRect, hBrush); SetRect(&fRect, rcWin.right - siFrame.cx, rcWin.top, rcWin.right, rcWin.bottom); FillRect(hDC, &fRect, hBrush); InflateRect(&rcWin, -siFrame.cx, 0); } if (siFrame.cy > 0) { SetRect(&fRect, rcWin.left, rcWin.top, rcWin.right, rcWin.top + siFrame.cy); FillRect(hDC, &fRect, hBrush); SetRect(&fRect, rcWin.left, rcWin.bottom - siFrame.cy, rcWin.right, rcWin.bottom); FillRect(hDC, &fRect, hBrush); InflateRect(&rcWin, 0, -siFrame.cy); } /* Draw the interior frame if we had a border */ if (siFrame.cx > 0 || siFrame.cy > 0) { #if 0 // See the remark above SetRect(&fRect, rcWin.left, rcWin.top, rcWin.right, rcWin.bottom); FrameRect(hDC, &fRect, GetSysColorBrush(COLOR_WINDOWFRAME)); #endif InflateRect(&rcWin, (siFrame.cx > 0 ? -1 : 0), (siFrame.cy > 0 ? -1 : 0)); } /* Draw the console window title bar */ hBrush = GetSysColorBrush(COLOR_BTNFACE); /* Draw the system menu (left button) */ SetRect(&fRect, rcWin.left, rcWin.top, rcWin.left + siButton.cx, rcWin.top + siButton.cy - 2); // DrawFrameControl(hDC, &fRect, DFC_CAPTION, DFCS_CAPTIONCLOSE); FillRect(hDC, &fRect, hBrush); fRect.right++; // Separation /* Draw the caption bar */ SetRect(&fRect, fRect.right, fRect.top, rcWin.right - 2 * (siButton.cx + 1), fRect.bottom); FillRect(hDC, &fRect, GetSysColorBrush(COLOR_ACTIVECAPTION)); fRect.right++; // Separation /* Draw the minimize menu (first right button) */ SetRect(&fRect, fRect.right, fRect.top, fRect.right + siButton.cx, fRect.bottom); // DrawFrameControl(hDC, &fRect, DFC_CAPTION, DFCS_CAPTIONMIN); FillRect(hDC, &fRect, hBrush); fRect.right++; // Separation /* Draw the maximize menu (second right button) */ SetRect(&fRect, fRect.right, fRect.top, fRect.right + siButton.cx, fRect.bottom); // DrawFrameControl(hDC, &fRect, DFC_CAPTION, DFCS_CAPTIONMAX); FillRect(hDC, &fRect, hBrush); rcWin.top += siButton.cy - 1; /* Add the scrollbars if needed */ if (siScroll.cy > 0 || siScroll.cx > 0) { LONG right, bottom; right = rcWin.right; bottom = rcWin.bottom; /* * If both the horizontal and vertical scrollbars are present, * reserve some space for the "dead square" at the bottom right. */ if (siScroll.cy > 0 && siScroll.cx > 0) { right -= (1 + siScroll.cx); bottom -= (1 + siScroll.cy); } hBrush = GetSysColorBrush(COLOR_SCROLLBAR); /* Horizontal scrollbar */ if (siScroll.cy > 0) { SetRect(&fRect, rcWin.left, rcWin.bottom - siScroll.cy, right, rcWin.bottom); FillRect(hDC, &fRect, hBrush); } /* Vertical scrollbar */ if (siScroll.cx > 0) { SetRect(&fRect, rcWin.right - siScroll.cx, rcWin.top, rcWin.right, bottom); FillRect(hDC, &fRect, hBrush); } /* * If both the horizontal and vertical scrollbars are present, * draw the "dead square" at the bottom right. */ if (siScroll.cy > 0 && siScroll.cx > 0) { SetRect(&fRect, rcWin.right - siScroll.cx, rcWin.bottom - siScroll.cy, rcWin.right, rcWin.bottom); FillRect(hDC, &fRect, hBrush); } // NOTE: If an additional exterior frame is needed, remove +1 for each direction rcWin.right -= siScroll.cx; rcWin.bottom -= siScroll.cy; } /* Draw the console background */ hBrush = CreateSolidBrush(pConInfo->ColorTable[BkgdAttribFromAttrib(pConInfo->ScreenAttributes)]); FillRect(hDC, &rcWin, hBrush); DeleteObject(hBrush); }
static void RelayoutTocItem(LPNMTVCUSTOMDRAW ntvcd) { // code inspired by http://www.codeguru.com/cpp/controls/treeview/multiview/article.php/c3985/ LPNMCUSTOMDRAW ncd = &ntvcd->nmcd; HWND hTV = ncd->hdr.hwndFrom; HTREEITEM hItem = (HTREEITEM)ncd->dwItemSpec; RECT rcItem; if (0 == ncd->rc.right - ncd->rc.left || 0 == ncd->rc.bottom - ncd->rc.top) return; if (!TreeView_GetItemRect(hTV, hItem, &rcItem, TRUE)) return; if (rcItem.right > ncd->rc.right) rcItem.right = ncd->rc.right; // Clear the label RECT rcFullWidth = rcItem; rcFullWidth.right = ncd->rc.right; FillRect(ncd->hdc, &rcFullWidth, GetSysColorBrush(COLOR_WINDOW)); // Get the label's text WCHAR szText[MAX_PATH]; TVITEM item; item.hItem = hItem; item.mask = TVIF_TEXT | TVIF_PARAM; item.pszText = szText; item.cchTextMax = MAX_PATH; TreeView_GetItem(hTV, &item); // Draw the page number right-aligned (if there is one) WindowInfo *win = FindWindowInfoByHwnd(hTV); DocTocItem *tocItem = (DocTocItem *)item.lParam; ScopedMem<WCHAR> label; if (tocItem->pageNo && win && win->IsDocLoaded()) { label.Set(win->ctrl->GetPageLabel(tocItem->pageNo)); label.Set(str::Join(L" ", label)); } if (label && str::EndsWith(item.pszText, label)) { RECT rcPageNo = rcFullWidth; InflateRect(&rcPageNo, -2, -1); SIZE txtSize; GetTextExtentPoint32(ncd->hdc, label, str::Len(label), &txtSize); rcPageNo.left = rcPageNo.right - txtSize.cx; SetTextColor(ncd->hdc, GetSysColor(COLOR_WINDOWTEXT)); SetBkColor(ncd->hdc, GetSysColor(COLOR_WINDOW)); DrawText(ncd->hdc, label, -1, &rcPageNo, DT_SINGLELINE | DT_VCENTER | DT_NOPREFIX); // Reduce the size of the label and cut off the page number rcItem.right = std::max(rcItem.right - txtSize.cx, 0); szText[str::Len(szText) - str::Len(label)] = '\0'; } SetTextColor(ncd->hdc, ntvcd->clrText); SetBkColor(ncd->hdc, ntvcd->clrTextBk); // Draw the focus rectangle (including proper background color) HBRUSH brushBg = CreateSolidBrush(ntvcd->clrTextBk); FillRect(ncd->hdc, &rcItem, brushBg); DeleteObject(brushBg); if ((ncd->uItemState & CDIS_FOCUS)) DrawFocusRect(ncd->hdc, &rcItem); InflateRect(&rcItem, -2, -1); DrawText(ncd->hdc, szText, -1, &rcItem, DT_SINGLELINE | DT_VCENTER | DT_NOPREFIX | DT_WORD_ELLIPSIS); }