// WM_PAINT message handler. LRESULT ClsFlatButton::OnPaint( ClsDC *pDC ) { // Input DC? if ( pDC ) PaintControl( pDC ); else { ClsPaintDC dc( this ); PaintControl( &dc ); } return 0; }
static void RepaintControl(HWND hWnd) { HDC hDC = GetDC(hWnd); PaintControl(hWnd,hDC); ReleaseDC(hWnd,hDC); }
LRESULT AeroControlBase::ProgressbarWindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { switch (uMsg) { 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); RECT rc; GetWindowRect(hWnd, &rc); MapWindowPoints(NULL, hWnd, (LPPOINT)&rc, 2); if (hdc) { PaintControl(hWnd, hdc, &ps.rcPaint, false); BP_PAINTPARAMS params = { sizeof(BP_PAINTPARAMS) }; params.dwFlags = 0L; HDC hdcPaint = NULL; HPAINTBUFFER hBufferedPaint = BeginBufferedPaint(hdc, &rc, BPBF_TOPDOWNDIB, ¶ms, &hdcPaint); if (hdcPaint) { COLORREF cr = RGB(0x00, 0x00, 0x00); SetPixel(hdcPaint, 0, 0, cr); SetPixel(hdcPaint, 0, RECTHEIGHT(rc) - 1, cr); SetPixel(hdcPaint, RECTWIDTH(rc) - 1, 0, cr); SetPixel(hdcPaint, RECTWIDTH(rc) - 1, RECTHEIGHT(rc) - 1, cr); EndBufferedPaint(hBufferedPaint, TRUE); } } EndPaint(hWnd, &ps); return 0; } break; case WM_NCDESTROY: case WM_DESTROY: RemoveWindowSubclass(hWnd, SubclassProc, Static); subclassedControls.erase(hWnd); break; } return DefSubclassProc(hWnd, uMsg, wParam, lParam); }
void MoveKnob( HDC hScreenDC, int nPos, PFADERINFO pFI ) ///////////////////////////////////////////////////////////////////////////// { // if above top of fader, put at top of fader if( nPos < 2 ) nPos = 2; // if below bottom of fader, put at bottom of fader if( nPos > (pFI->nWindowY - pFI->bmFader.bmHeight - 2) ) nPos = pFI->nWindowY - pFI->bmFader.bmHeight - 2; pFI->nBitmapPos = nPos; // Draw the new knob PaintControl( hScreenDC, pFI ); }
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); }
LRESULT CALLBACK WndProcc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { PAERO_SUBCLASS_WND_DATA pWndData = (PAERO_SUBCLASS_WND_DATA)GetProp(hWnd, WINDOW_DATA_STRING); ASSERT(pWndData); ASSERT(pWndData->m_pDwmApiImpl); WNDPROC pOldProc = pWndData->m_oldWndProc; ASSERT(pOldProc); BOOL bCompositionEnabled = pWndData->m_pDwmApiImpl->IsDwmCompositionEnabled(); /// /// if aero glass is turned off and if we are not in destruction code, /// just call the original wnd proc we had prior to subclassing: /// if(WM_COMMAND!=uMsg && WM_DWMCOMPOSITIONCHANGED!=uMsg && WM_DESTROY!=uMsg && WM_NCDESTROY!=uMsg && !bCompositionEnabled) return CallWindowProc(pOldProc, hWnd, uMsg, wParam, lParam); if (uMsg == pWndData->m_uiRedrawMsg) { HWND hControl = (HWND)lParam; ASSERT(hControl); ASSERT(::IsWindow(hControl)); PAERO_SUBCLASS_WND_DATA pCtrlData = (PAERO_SUBCLASS_WND_DATA)GetProp(hControl, WINDOW_DATA_STRING); if(pCtrlData && pCtrlData->m_dwFlags & WD_IN_PAINT_CONTROL) { HDC hdc = GetDC(hControl); if(hdc) { RECT rc; VERIFY(GetWindowRect(hControl, &rc)); VERIFY(MapWindowPoints(NULL, hControl, (LPPOINT) &rc, 2)); PaintControl(hControl, hdc, &rc, (pCtrlData->m_dwFlags & WD_DRAW_BORDER)!=0); VERIFY(1==ReleaseDC(hControl, hdc)); } pCtrlData->m_dwFlags &= ~WD_IN_PAINT_CONTROL; return 0; } } switch(uMsg) { case WM_CTLCOLORSTATIC: { HWND hControl = (HWND)lParam; ASSERT(hControl); ASSERT(IsWindow(hControl)); PAERO_SUBCLASS_WND_DATA pCtrlData = (PAERO_SUBCLASS_WND_DATA)GetProp(hControl, WINDOW_DATA_STRING); if(pCtrlData) { if(pCtrlData->m_dwFlags&WD_RETURN_BLACK_BRUSH) return (LRESULT)GetStockObject(BLACK_BRUSH); else if(pCtrlData->m_dwFlags&WD_RETURN_WHITE_BRUSH) return (LRESULT)GetStockObject(WHITE_BRUSH); else { pCtrlData->m_dwFlags|=WD_IN_PAINT_CONTROL; PostMessage((HWND)lParam, pWndData->m_uiRedrawMsg, 0, NULL); } } } break; case WM_CTLCOLOREDIT: { PAERO_SUBCLASS_WND_DATA pCtrlData = (PAERO_SUBCLASS_WND_DATA)GetProp((HWND)lParam, WINDOW_DATA_STRING); if(pCtrlData) pCtrlData->m_dwFlags|=WD_IN_PAINT_CONTROL; PostMessage((HWND)lParam, pWndData->m_uiRedrawMsg, 0, NULL); } break; case WM_PAINT: { if(!IsIconic(hWnd) && !(pWndData->m_dwFlags&WD_NO_FRAME_EXTEND)) { PAINTSTRUCT ps; HDC hdc = BeginPaint(hWnd, &ps); /// /// we have to paint the *entire* client area in black, not only the /// paint area inside ps, because otherwise we get ugly areas of white /// if we partially move the window out of the desktop and back in again: /// /// MARGINS marGlassInset = {0, 0, 0, 302}; // -1 means the whole window if(hdc && pWndData->m_pDwmApiImpl->IsDwmCompositionEnabled() && SUCCEEDED(pWndData->m_pDwmApiImpl->DwmExtendFrameIntoClientArea(hWnd, &marGlassInset))) { RECT rcClient; VERIFY(GetClientRect(hWnd, &rcClient)); VERIFY(PatBlt(hdc, 0, 0, RECTWIDTH(rcClient), RECTHEIGHT(rcClient), BLACKNESS)); } EndPaint(hWnd, &ps); return 1; } } break; case WM_COMMAND: { if(bCompositionEnabled) { if(LBN_SELCHANGE==HIWORD(wParam)) { InvalidateRgn((HWND)lParam, NULL, TRUE); VERIFY(UpdateWindow((HWND)lParam)); } } if(ACN_STOP==HIWORD(wParam)) { /// /// if it is an animation control that has just stopped playing, /// reset the WD_PLAY flag so it repaints itself properly again if /// e.g. Aero is turned off an on again: /// PAERO_SUBCLASS_WND_DATA pCtrlData = (PAERO_SUBCLASS_WND_DATA)GetProp((HWND)lParam, WINDOW_DATA_STRING); if(pCtrlData) { pCtrlData->m_dwFlags&=~WD_PLAY; } } if(ACN_START==HIWORD(wParam)) { PAERO_SUBCLASS_WND_DATA pCtrlData = (PAERO_SUBCLASS_WND_DATA)GetProp((HWND)lParam, WINDOW_DATA_STRING); if(pCtrlData) { pCtrlData->m_dwFlags|=WD_PLAY; } } } break; case WM_NOTIFY: { LPNMHDR lpnmh = (LPNMHDR)lParam; if(lpnmh) { ASSERT(lpnmh->hwndFrom); ASSERT(IsWindow(lpnmh->hwndFrom)); switch(lpnmh->code) { case LVN_ITEMCHANGED: { /// /// if we select and deselect list view items, /// its header control sometimes vanishes so /// we have to force a redraw: /// HWND hHeader = ListView_GetHeader(lpnmh->hwndFrom); if(hHeader) { InvalidateRgn(hHeader, NULL, TRUE); VERIFY(UpdateWindow(hHeader)); } } break; default: break; } } } break; case WM_DESTROY: ASSERT(pWndData->m_pUxTheme); ASSERT(pWndData->m_pDwmApiImpl); VERIFY(SUCCEEDED(pWndData->m_pUxTheme->BufferedPaintUnInit())); delete pWndData->m_pUxTheme; delete pWndData->m_pDwmApiImpl; if(WndProcc==(WNDPROC)GetWindowLongPtr(hWnd, GWLP_WNDPROC)) { VERIFY(WndProcc==(WNDPROC) SetWindowLongPtr(hWnd, GWLP_WNDPROC, (LONG_PTR) pWndData->m_oldWndProc)); VERIFY(pWndData==RemoveProp(hWnd, WINDOW_DATA_STRING)); VERIFY(!LocalFree(pWndData)); } break; case WM_NCDESTROY: if(WndProcc==(WNDPROC)GetWindowLongPtr(hWnd, GWLP_WNDPROC)) { VERIFY(WndProcc==(WNDPROC) SetWindowLongPtr(hWnd, GWLP_WNDPROC, (LONG_PTR) pWndData->m_oldWndProc)); VERIFY(pWndData==RemoveProp(hWnd, WINDOW_DATA_STRING)); VERIFY(!LocalFree(pWndData)); } break; } return CallWindowProc(pOldProc, hWnd, uMsg, wParam, lParam); }
LONG WINAPI FaderWndProc( HWND hWnd, UINT iMessage, WPARAM wParam, LPARAM lParam ) ///////////////////////////////////////////////////////////////////////////// { PAINTSTRUCT ps; PFADERINFO pFI = (PFADERINFO)GetWindowLong( hWnd, GWL_USERDATA ); HWND hParentWnd = GetParent( hWnd ); switch( iMessage ) { case WM_GETDLGCODE: return( DLGC_WANTARROWS ); case WM_SETFOCUS: if( pFI ) { CreateCaret( hWnd, (HBITMAP)1, pFI->bmFader.bmWidth - 5, pFI->bmFader.bmHeight - CARET_OFFSET ); SetCaretPos( pFI->nBitmapX + 2, pFI->nBitmapPos + (CARET_OFFSET/2) ); ShowCaret( hWnd ); pFI->bHasFocus = TRUE; } break; case WM_KILLFOCUS: if( pFI ) pFI->bHasFocus = FALSE; HideCaret( hWnd ); DestroyCaret(); break; case WM_APPCOMMAND: switch( GET_APPCOMMAND_LPARAM(lParam) ) { case APPCOMMAND_VOLUME_MUTE: PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_BOTTOM, (LPARAM)hWnd ); return( TRUE ); case APPCOMMAND_VOLUME_UP: PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_LINEUP, (LPARAM)hWnd ); return( TRUE ); case APPCOMMAND_VOLUME_DOWN: PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_LINEDOWN, (LPARAM)hWnd ); return( TRUE ); default: return( DefWindowProc( hWnd, iMessage, wParam, lParam ) ); } break; case WM_KEYDOWN: /* Keyboard Interface for Fader */ switch( wParam ) { case VK_TAB: // pass this on to the parent //PostMessage( hParentWnd, iMessage, wParam, lParam ); break; case VK_RIGHT: case VK_DOWN: PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_LINEDOWN, (LPARAM)hWnd ); break; case VK_LEFT: case VK_UP: PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_LINEUP, (LPARAM)hWnd ); break; case VK_PRIOR: PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_PAGEUP, (LPARAM)hWnd ); break; case VK_NEXT: PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_PAGEDOWN, (LPARAM)hWnd ); break; case VK_HOME: PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_TOP, (LPARAM)hWnd ); break; case VK_END: PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_BOTTOM, (LPARAM)hWnd ); break; } break; case WM_LBUTTONUP: ReleaseCapture(); if( pFI ) { // we know this control has the focus SetCaretPos( pFI->nBitmapX + 2, pFI->nBitmapPos + (CARET_OFFSET/2) ); ShowCaret( hWnd ); pFI->bMouseDown = FALSE; } break; case WM_LBUTTONDOWN: SetFocus( hWnd ); SetCapture( hWnd ); HideCaret( hWnd ); if( pFI ) { pFI->bMouseDown = TRUE; /* Fall Through */ } case WM_MOUSEMOVE: //fwKeys = wParam; // key flags //xPos = LOWORD(lParam); // horizontal position of cursor //yPos = HIWORD(lParam); // vertical position of cursor (zero at the top) if( pFI ) { if( pFI->bMouseDown ) { short X = LOWORD( lParam ); short Y = HIWORD( lParam ); WORD wPos; int nScale = pFI->nWindowY - pFI->bmFader.bmHeight; // make sure we don't go out of bounds if( Y > (pFI->nWindowY - (pFI->bmFader.bmHeight/2)) ) Y = (pFI->nWindowY - (pFI->bmFader.bmHeight/2)); if( Y < (pFI->bmFader.bmHeight/2) ) Y = (pFI->bmFader.bmHeight/2); Y -= (pFI->bmFader.bmHeight/2); if( Y > nScale ) Y = nScale; wPos = pFI->nMax - (((int)Y * pFI->nMax) / nScale); PostMessage( hParentWnd, WM_VSCROLL, MAKELONG( SB_THUMBTRACK, wPos ), (LPARAM)hWnd ); } } break; case WM_MOUSEWHEEL: { short fwKeys = LOWORD( wParam ); short nZDelta = HIWORD( wParam ); short nX = LOWORD( lParam ); short nY = HIWORD( lParam ); POINT Point; HWND hParent; // long CntlID; // what window is the mouse currently above? Point.x = nX; Point.y = nY; hWnd = WindowFromPoint( Point ); hParent = GetParent( hWnd ); // if the parent of this window is not our parent, we are done if( hParent != hParentWnd ) return( 0L ); // is this one of our fader windows? /*********** CntlID = GetWindowLong( hWnd, GWL_ID ); switch( CntlID ) { case IDC_OUT1_VOLUME: case IDC_OUT2_VOLUME: case IDC_OUT3_VOLUME: case IDC_OUT4_VOLUME: break; default: return( 0L ); } ***********/ SetFocus( hWnd ); HideCaret( hWnd ); //sprintf( szBuffer, "fwKeys [%d] nZ [%d] nX [%d] nY [%d]", fwKeys, nZDelta, nX, nY ); //SetDlgItemText( GetParent( hWnd ), IDC_STATUS, szBuffer ); if( nZDelta > 0 ) PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_LINEUP, (LPARAM)hWnd ); else PostMessage( hParentWnd, WM_VSCROLL, (WPARAM)SB_LINEDOWN, (LPARAM)hWnd ); } break; case WM_SIZE: if( pFI ) { pFI->nWindowX = LOWORD( lParam ); pFI->nWindowY = HIWORD( lParam ); // Place the Knob at the top of the control pFI->nBitmapPos = pFI->nWindowY - pFI->bmFader.bmHeight - 2; pFI->nBitmapX = (pFI->nWindowX / 2) - (pFI->bmFader.bmWidth / 2); } break; case WM_CREATE: pFI = (PFADERINFO)malloc( sizeof( FADERINFO ) ); SetWindowLong( hWnd, GWL_USERDATA, (DWORD)pFI ); if( !pFI ) { MessageBox( NULL, TEXT("Fader: malloc failed!"), TEXT("LynxONE Mixer"), MB_OK | MB_ICONSTOP | MB_TASKMODAL ); break; } ZeroMemory( pFI, sizeof( FADERINFO ) ); pFI->hFader = LoadBitmap( AfxGetInstanceHandle(), MAKEINTRESOURCE( IDB_FADER ) ); pFI->hGradient = LoadBitmap( AfxGetInstanceHandle(), MAKEINTRESOURCE( IDB_GRADIENT ) ); GetObject( pFI->hFader, sizeof( BITMAP ), (LPSTR)&pFI->bmFader ); GetObject( pFI->hGradient, sizeof( BITMAP ), (LPSTR)&pFI->bmGradient ); break; case WM_DESTROY: if( pFI ) { DeleteObject( pFI->hFader ); DeleteObject( pFI->hGradient ); free( pFI ); } SetWindowLong( hWnd, GWL_USERDATA, (DWORD)0 ); break; case WM_PAINT: BeginPaint( hWnd, (LPPAINTSTRUCT)&ps ); if( pFI ) PaintControl( ps.hdc, pFI ); EndPaint( hWnd, (LPPAINTSTRUCT)&ps ); break; default: return( DefWindowProc( hWnd, iMessage, wParam, lParam ) ); } return( 0L ); }
LRESULT pascal HexViewWndProc(HWND hWnd, UINT iMsg, WPARAM wParam, LPARAM lParam) { switch (iMsg) { case WM_CREATE: { PHV p = Mem_Alloc(MEMF_ZEROINIT, sizeof(HexViewInfo)); HDC hDC = GetDC(0); int nHeight = -MulDiv(9, GetDeviceCaps(hDC, LOGPIXELSY), 72); ReleaseDC(0,hDC); p->hCreateFont = CreateFont(nHeight,0,0,0,FW_NORMAL,FALSE,FALSE,FALSE,ANSI_CHARSET,OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS,DEFAULT_QUALITY,FIXED_PITCH,"Courier New"); p->hFont = p->hCreateFont; p->BuffSize = 512; p->idCtl = GetWindowLong(hWnd, GWL_ID); SetWindowLong(hWnd, GWL_PHEXVIEW, (LONG)p); if (!hPenGutter) { hPenGutter = CreatePen(PS_SOLID,1,RGB(192,192,192)); hBrushRow = CreateSolidBrush(RGB(208,228,246)); } break; } case WM_SETFONT: { // PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); // p->hFont = (HFONT)wParam; // if (lParam) InvalidateRect(hWnd, NULL, FALSE); break; } case WM_GETFONT: { PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); return (LRESULT)(p->hFont); } case WM_GETDLGCODE: return DLGC_WANTARROWS; case WM_ERASEBKGND: return 1; case WM_PRINTCLIENT: PaintControl(hWnd, (HDC)wParam); break; case WM_PAINT: { PAINTSTRUCT ps; HDC hDC = (wParam ? (HDC)wParam : BeginPaint(hWnd,&ps)); PaintControl(hWnd, hDC); if (wParam) ValidateRect(hWnd,NULL); else EndPaint(hWnd, &ps); break; } case WM_LBUTTONDOWN: { PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); UINT oldCaret = p->iCaret; HandleMouseClick(hWnd,LOWORD(lParam),HIWORD(lParam)); if (p->iCaret != oldCaret) SendMessage(GetParent(hWnd),WM_COMMAND,MAKEWPARAM(p->idCtl,HVN_OFFSET_CHANGED),(LPARAM)hWnd); if (GetFocus()==hWnd) RepaintControl(hWnd); else SetFocus(hWnd); break; } case WM_KEYDOWN: { PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); UINT oldCaret = p->iCaret; if (wParam == VK_LEFT) { if (oldCaret) p->iCaret--; } else if (wParam==VK_RIGHT) { if ((oldCaret+1) < p->BuffSize) p->iCaret++; } else if (wParam==VK_UP) { if (oldCaret>=COLS) p->iCaret -= COLS; else SendMessage(GetParent(hWnd),WM_COMMAND, MAKEWPARAM(p->idCtl,HVN_LINEUP),(LPARAM)hWnd); } else if (wParam==VK_DOWN) { if ((oldCaret+COLS) < p->BuffSize) p->iCaret += COLS; else SendMessage(GetParent(hWnd),WM_COMMAND, MAKEWPARAM(p->idCtl,HVN_LINEDOWN),(LPARAM)hWnd); } else if (wParam==VK_PRIOR) { SendMessage(GetParent(hWnd),WM_COMMAND, MAKEWPARAM(p->idCtl,HVN_PAGEUP),(LPARAM)hWnd); return 0; } else if (wParam==VK_NEXT) { SendMessage(GetParent(hWnd),WM_COMMAND, MAKEWPARAM(p->idCtl,HVN_PAGEDOWN),(LPARAM)hWnd); return 0; } if (p->iCaret != oldCaret) { RepaintControl(hWnd); SendMessage(GetParent(hWnd),WM_COMMAND,MAKEWPARAM(p->idCtl,HVN_OFFSET_CHANGED),(LPARAM)hWnd); } break; } case WM_SETFOCUS: case WM_KILLFOCUS: case HVM_REPAINT: RepaintControl(hWnd); break; /* ctrl-specific messages */ case HVM_GETBUFFPTR: { PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); return (LRESULT)(p->buffer); } case HVM_SETBUFFSIZE: { PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); p = Mem_ReAlloc(p,MEMF_ZEROINIT,sizeof(HexViewInfo)-512+wParam); p->BuffSize = (UINT)wParam; if (p->iCaret>p->BuffSize) p->iCaret = 0; if (lParam) RepaintControl(hWnd); // Can be used to set a new buffer size. wParam = new buffer size in bytes. // Returns TRUE on success. // IMPORTANT NOTE: any previously stored buffer pointer will be invalidated // by this function. break; } case HVM_GETOFFSET: { PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); return (LRESULT)(p->iCaret); } case HVM_SETOFFSET: { PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); if (wParam<p->BuffSize && wParam!=p->iCaret) { p->iCaret = (UINT)wParam; if (lParam) RepaintControl(hWnd); } return (LRESULT)(p->iCaret); } case HVM_GETDIMENSIONS: { PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); HDC hDC = GetDC(0); HFONT hFont = SelectObject(hDC,p->hFont); int w,h; SIZE step; GetCharSpacing(hDC,&step); SelectObject(hDC,hFont); ReleaseDC(0,hDC); h = step.cy+Y_PAD; w = step.cx*(3 + 3*COLS) + COLS*X_PAD + 16; return MAKELRESULT(w,h); } case WM_NCDESTROY: { PHV p = (PHV)GetWindowLong(hWnd,GWL_PHEXVIEW); p->hBm = SelectObject(p->hMemDC, p->hBm); DeleteObject(p->hBm); DeleteDC(p->hMemDC); if (p->hCreateFont) DeleteObject(p->hCreateFont); Mem_Free(p); break; } default: return DefWindowProc(hWnd,iMsg,wParam,lParam); } return 0; }