win32context.cpp
来自「这是VCF框架的代码」· C++ 代码 · 共 2,636 行 · 第 1/5 页
CPP
2,636 行
::SelectObject( dc_, oldFont ); ::DeleteObject( font ); releaseHandle(); return textSize.cy;}void Win32Context::setTextAlignment( const bool& alignTobaseline ){ alignToBaseline_ = alignTobaseline;}bool Win32Context::isTextAlignedToBaseline(){ return alignToBaseline_;}/***Utility function to draw a transparent bitmap from MSDN*HOWTO: Drawing Transparent Bitmaps*Article ID: Q79212*JC: This is an awfult lot of shit to just draw a transparent bmp.*Maybe this will be revisited ???*/void Win32Context::drawTransparentBitmap(HDC hdc, HBITMAP hBitmap, long xStart, long yStart, COLORREF cTransparentColor){ BITMAP bm; COLORREF cColor; HBITMAP bmAndBack, bmAndObject, bmAndMem, bmSave; HBITMAP bmBackOld, bmObjectOld, bmMemOld, bmSaveOld; HDC hdcMem, hdcBack, hdcObject, hdcTemp, hdcSave; POINT ptSize; hdcTemp = CreateCompatibleDC( NULL );//hdc); SelectObject(hdcTemp, hBitmap); // Select the bitmap GetObject(hBitmap, sizeof(BITMAP), (LPSTR)&bm); ptSize.x = bm.bmWidth; // Get width of bitmap ptSize.y = bm.bmHeight; // Get height of bitmap DPtoLP(hdcTemp, &ptSize, 1); // Convert from device // to logical points // Create some DCs to hold temporary data. hdcBack = CreateCompatibleDC(hdc); hdcObject = CreateCompatibleDC(hdc); hdcMem = CreateCompatibleDC(hdc); hdcSave = CreateCompatibleDC(hdc); // Create a bitmap for each DC. DCs are required for a number of // GDI functions. // Monochrome DC bmAndBack = CreateBitmap(ptSize.x, ptSize.y, 1, 1, NULL); // Monochrome DC bmAndObject = CreateBitmap(ptSize.x, ptSize.y, 1, 1, NULL); bmAndMem = CreateCompatibleBitmap(hdc, ptSize.x, ptSize.y); bmSave = CreateCompatibleBitmap(hdc, ptSize.x, ptSize.y); // Each DC must select a bitmap object to store pixel data. bmBackOld = (HBITMAP)SelectObject(hdcBack, bmAndBack); bmObjectOld = (HBITMAP)SelectObject(hdcObject, bmAndObject); bmMemOld = (HBITMAP)SelectObject(hdcMem, bmAndMem); bmSaveOld = (HBITMAP)SelectObject(hdcSave, bmSave); // Set proper mapping mode. SetMapMode(hdcTemp, GetMapMode(hdc)); // Save the bitmap sent here, because it will be overwritten. BitBlt(hdcSave, 0, 0, ptSize.x, ptSize.y, hdcTemp, 0, 0, SRCCOPY); // Set the background color of the source DC to the color. // contained in the parts of the bitmap that should be transparent cColor = SetBkColor(hdcTemp, cTransparentColor); // Create the object mask for the bitmap by performing a BitBlt // from the source bitmap to a monochrome bitmap. BitBlt(hdcObject, 0, 0, ptSize.x, ptSize.y, hdcTemp, 0, 0, SRCCOPY); // Set the background color of the source DC back to the original // color. SetBkColor(hdcTemp, cColor); // Create the inverse of the object mask. BitBlt(hdcBack, 0, 0, ptSize.x, ptSize.y, hdcObject, 0, 0, NOTSRCCOPY); // Copy the background of the main DC to the destination. BitBlt(hdcMem, 0, 0, ptSize.x, ptSize.y, hdc, xStart, yStart, SRCCOPY); // Mask out the places where the bitmap will be placed. BitBlt(hdcMem, 0, 0, ptSize.x, ptSize.y, hdcObject, 0, 0, SRCAND); // Mask out the transparent colored pixels on the bitmap. BitBlt(hdcTemp, 0, 0, ptSize.x, ptSize.y, hdcBack, 0, 0, SRCAND); // XOR the bitmap with the background on the destination DC. BitBlt(hdcMem, 0, 0, ptSize.x, ptSize.y, hdcTemp, 0, 0, SRCPAINT); // Copy the destination to the screen. BitBlt(hdc, xStart, yStart, ptSize.x, ptSize.y, hdcMem, 0, 0, SRCCOPY); // Place the original bitmap back into the bitmap sent here. BitBlt(hdcTemp, 0, 0, ptSize.x, ptSize.y, hdcSave, 0, 0, SRCCOPY); // Delete the memory bitmaps. DeleteObject(SelectObject(hdcBack, bmBackOld)); DeleteObject(SelectObject(hdcObject, bmObjectOld)); DeleteObject(SelectObject(hdcMem, bmMemOld)); DeleteObject(SelectObject(hdcSave, bmSaveOld)); // Delete the memory DCs. DeleteDC(hdcMem); DeleteDC(hdcBack); DeleteDC(hdcObject); DeleteDC(hdcSave); DeleteDC(hdcTemp);}void Win32Context::setClippingRect( Rect* clipRect ){ checkHandle(); if ( NULL != clipRGN_ ) { if ( !::DeleteObject( clipRGN_ ) ) { StringUtils::traceWithArgs( Format("Error in DeleteObject( %p )\n") % clipRGN_ % GetLastError() ); } } clipRGN_ = NULL; if ( NULL != clipRect ) { if ( !clipRect->isNull() ) { clipRGN_ = CreateRectRgn( (long)clipRect->left_ + origin_.x_, (long)clipRect->top_ + origin_.y_, (long)clipRect->right_ + origin_.x_, (long)clipRect->bottom_ + origin_.y_); } else { clipRGN_ = NULL; } } if ( ERROR == ::SelectClipRgn( dc_, clipRGN_ ) ){ StringUtils::traceWithArgs( Format( "Error in SelectClipRgn( %p, %p )\n" ) % dc_ % clipRGN_ % GetLastError() ); } releaseHandle();}void Win32Context::setClippingPath( Path* clippingPath ){ checkHandle(); if ( NULL != clipRGN_ ) { ::DeleteObject( clipRGN_ ); } clipRGN_ = NULL; if ( NULL != clippingPath ) { ::BeginPath( dc_ ); std::vector<PathPoint> points; Matrix2D* currentXFrm = context_->getCurrentTransform(); clippingPath->getPoints( points, currentXFrm ); std::vector<PathPoint>::iterator it = points.begin(); while ( it != points.end() ) { const PathPoint& pt = *it; switch ( pt.type_ ){ case PathPoint::ptMoveTo: { MoveToEx( dc_, (long)pt.point_.x_ + origin_.x_, (long)pt.point_.y_ + origin_.y_, NULL ); } break; case PathPoint::ptLineTo: { LineTo( dc_, (long)pt.point_.x_ + origin_.x_, (long)pt.point_.y_ + origin_.y_ ); } break; case PathPoint::ptQuadTo: { } break; case PathPoint::ptCubicTo: { } break; case PathPoint::ptClose: { LineTo( dc_, (long)pt.point_.x_ + origin_.x_, (long)pt.point_.y_ + origin_.y_ ); } break; } it++; } ::EndPath( dc_ ); clipRGN_ = ::PathToRegion( dc_ ); } ::SelectClipRgn( dc_, clipRGN_ ); releaseHandle();}void Win32Context::drawThemeSelectionRect( Rect* rect, DrawUIState& state ){ checkHandle(); RECT r = {0,0,0,0}; r.left = (long)rect->left_; r.top = (long)rect->top_; r.right = (long)rect->right_; r.bottom = (long)rect->bottom_; int err = ::DrawFocusRect( dc_, &r ); releaseHandle();}void Win32Context::drawThemeFocusRect( Rect* rect, DrawUIState& state ){ checkHandle(); RECT r = {0,0,0,0}; r.left = (long)rect->left_; r.top = (long)rect->top_; r.right = (long)rect->right_; r.bottom = (long)rect->bottom_; int err = ::DrawFocusRect( dc_, &r ); releaseHandle();}void Win32Context::drawThemeButtonFocusRect( Rect* rect ){ Rect focusRect = *rect; focusRect.inflate( -4, -4 ); DrawUIState state; drawThemeFocusRect( &focusRect, state );}void Win32Context::drawThemeButtonRect( Rect* rect, ButtonState& state, Rect* captionRect ){ checkHandle(); RECT btnRect; btnRect.left = rect->left_; btnRect.top = rect->top_; btnRect.right = rect->right_; btnRect.bottom = rect->bottom_; HTHEME theme = NULL; if ( Win32VisualStylesWrapper::IsThemeActive() ) { theme = Win32VisualStylesWrapper::OpenThemeData( NULL, L"BUTTON" ); } if ( theme ) { int dcs = SaveDC( dc_ ); int btnState = 0; if ( !state.isEnabled() ) { btnState = PBS_DISABLED; } else { btnState |= state.isHighlighted() ? PBS_HOT : PBS_NORMAL; btnState |= state.isDefaultButton() ? PBS_DEFAULTED : PBS_NORMAL; btnState = state.isPressed() ? PBS_PRESSED : btnState; } Win32VisualStylesWrapper::DrawThemeBackground(theme, dc_, BP_PUSHBUTTON, btnState, &btnRect, 0); SetBkMode(dc_, TRANSPARENT); VCF::Font btnFont = *context_->getCurrentFont(); HFONT font = NULL; if ( System::isUnicodeEnabled() ) { LOGFONTW* lf = (LOGFONTW*) btnFont.getFontPeer()->getFontHandleID(); font = ::CreateFontIndirectW( lf ); ::SelectObject( dc_, font ); } else { LOGFONTA* lf = (LOGFONTA*) btnFont.getFontPeer()->getFontHandleID(); font = ::CreateFontIndirectA( lf ); ::SelectObject( dc_, font ); } btnRect.left += 5; btnRect.right -= 5; Win32VisualStylesWrapper::DrawThemeText(theme, dc_, BP_PUSHBUTTON, btnState, state.buttonCaption_.c_str(), state.buttonCaption_.length(), DT_SINGLELINE | DT_CENTER | DT_VCENTER, NULL, &btnRect); Win32VisualStylesWrapper::CloseThemeData( theme ); RestoreDC(dc_, dcs ); DeleteObject( font ); } else { COLORREF backColor = ::GetSysColor( COLOR_3DFACE ); HBRUSH backBrush = CreateSolidBrush( backColor ); HPEN hilightPen = CreatePen( PS_SOLID, 0, ::GetSysColor( COLOR_3DHIGHLIGHT ) ); HPEN shadowPen = CreatePen( PS_SOLID, 0, ::GetSysColor( COLOR_3DSHADOW ) ); HPEN blackPen = CreatePen( PS_SOLID, 0, 0 ); HBRUSH oldBrush = (HBRUSH)::SelectObject( dc_, backBrush ); ::FillRect( dc_, &btnRect, backBrush ); bool isPressed = state.isPressed(); HPEN oldPen = NULL; RECT tmpRect = btnRect; //InflateRect( &tmpRect, -1, -1 ); if ( state.isDefaultButton() ) { InflateRect( &tmpRect, -1, -1 ); } RECT capRect = btnRect; if ( NULL != captionRect ) { capRect.left = captionRect->left_; capRect.top = captionRect->top_; capRect.right = captionRect->right_; capRect.bottom = captionRect->bottom_; } if ( true == isPressed ) { HBRUSH shadowBrush = CreateSolidBrush( ::GetSysColor( COLOR_3DSHADOW ) ); ::FrameRect( dc_, &tmpRect, shadowBrush ); DeleteObject( shadowBrush ); ::OffsetRect( &capRect, 1, 1 ); } else { oldPen = (HPEN) ::SelectObject( dc_, hilightPen ); ::MoveToEx( dc_, tmpRect.right, tmpRect.top, NULL ); ::LineTo( dc_, tmpRect.left, tmpRect.top ); ::LineTo( dc_, tmpRect.left, tmpRect.bottom-1 ); ::SelectObject( dc_, shadowPen ); ::MoveToEx( dc_, tmpRect.right-2, tmpRect.top+1, NULL ); ::LineTo( dc_, tmpRect.right-2, tmpRect.bottom-2 ); ::LineTo( dc_, tmpRect.left, tmpRect.bottom-2 ); ::SelectObject( dc_, blackPen ); ::MoveToEx( dc_, tmpRect.right-1, tmpRect.top, NULL ); ::LineTo( dc_, tmpRect.right-1, tmpRect.bottom-1 ); ::LineTo( dc_, tmpRect.left-1, tmpRect.bottom-1 ); /* ::MoveToEx( dc_, tmpRect.right, tmpRect.top, NULL ); ::LineTo( dc_, tmpRect.left, tmpRect.top ); ::LineTo( dc_, tmpRect.left, tmpRect.bottom ); ::SelectObject( dc_, shadowPen ); ::MoveToEx( dc_, tmpRect.right-1, tmpRect.top+1, NULL ); ::LineTo( dc_, tmpRect.right-1, tmpRect.bottom-1 ); ::LineTo( dc_, tmpRect.left, tmpRect.bottom-1 ); ::SelectObject( dc_, blackPen ); ::MoveToEx( dc_, tmpRect.right-1, tmpRect.top, NULL ); ::LineTo( dc_, tmpRect.right, tmpRect.bottom ); ::LineTo( dc_, tmpRect.left, tmpRect.bottom ); */ } bool enabled = state.isEnabled(); HFONT font = NULL; HFONT oldFont = NULL; VCF::Font btnFont = *context_->getCurrentFont(); Rect centerRect( capRect.left, capRect.top, capRect.right, capRect.bottom ); if ( System::isUnicodeEnabled() ) { LOGFONTW* lf = (LOGFONTW*) btnFont.getFontPeer()->getFontHandleID(); font = ::CreateFontIndirectW( lf ); oldFont = (HFONT) ::SelectObject( dc_, font ); ::DrawTextW( dc_, state.buttonCaption_.c_str(), -1, &capRect, DT_WORDBREAK | DT_CENTER | DT_CALCRECT); } else { LOGFONTA* lf = (LOGFONTA*) btnFont.getFontPeer()->getFontHandleID(); font = ::CreateFontIndirectA( lf ); oldFont = (HFONT) ::SelectObject( dc_, font ); ::DrawTextA( dc_, state.buttonCaption_.ansi_c_str(), -1, &capRect, DT_WORDBREAK | DT_CENTER | DT_CALCRECT); } ::OffsetRect( &capRect, (centerRect.getWidth() - (capRect.right - capRect.left))/2, (centerRect.getHeight() - (capRect.bottom - capRect.top))/2 ); int oldBkMode = SetBkMode( dc_, TRANSPARENT ); COLORREF textColor = 0; if ( true == enabled ) { textColor = ::GetSysColor( COLOR_BTNTEXT ); } else { textColor = ::GetSysColor( COLOR_GRAYTEXT ); } COLORREF oldTextColor = SetTextColor( dc_, textColor ); if ( false == enabled ) { SetTextColor( dc_, ::GetSysColor( COLOR_BTNHIGHLIGHT ) ); OffsetRect( &capRect, 1, 1 ); if ( System::isUnicodeEnabled() ) { ::DrawTextW( dc_, state.buttonCaption_.c_str(), -1, &capRect, DT_WORDBREAK | DT_CENTER); } else { ::DrawTextA( dc_, state.buttonCaption_.ansi_c_str(), -1, &capRect, DT_WORDBREAK | DT_CENTER); } OffsetRect( &capRect, -1, -1 ); SetTextColor( dc_, textColor ); } if ( System::isUnicodeEnabled() ) { ::DrawTextW( dc_, state.buttonCaption_.c_str(), -1, &capRect, DT_WORDBREAK | DT_CENTER); } else { ::DrawTextA( dc_, state.buttonCaption_.ansi_c_str(), -1, &capRect, DT_WORDBREAK | DT_CENTER); } SetTextColor( dc_, oldTextColor ); SetBkMode( dc_, oldBkMode ); ::SelectObject( dc_, oldFont ); ::DeleteObject( font ); /*if ( state.isFocused() ) { RECT focusRect = btnRect; InflateRect( &focusRect, -4, -4 ); ::DrawFocusRect( dc_, &focusRect ); }*/ if ( state.isDefaultButton() ) { RECT defRect = btnRect; //defRect.right -= 1; //defRect.bottom -= 1; FrameRect( dc_, &defRect, (HBRUSH)GetStockObject(BLACK_BRUSH) ); } if ( NULL != oldBrush ) { ::SelectObject( dc_, oldBrush ); } if ( NULL != oldPen ) { ::SelectObject( dc_, oldPen ); } ::DeleteObject( hilightPen ); ::DeleteObject( shadowPen ); ::DeleteObject( blackPen ); ::DeleteObject( backBrush ); } releaseHandle();}void Win32Context::drawThemeCheckboxRect( Rect* rect, ButtonState& state ){ checkHandle(); Rect tmp = *rect; HTHEME theme = NULL; if ( Win32VisualStylesWrapper::IsThemeActive() ) { theme = Win32VisualStylesWrapper::OpenThemeData( NULL, L"BUTTON" );
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?