void wxAuiMSWTabArt::DrawBorder(wxDC& dc, wxWindow* wnd, const wxRect& rect) { if ( !IsThemed() ) { wxAuiGenericTabArt::DrawBorder(dc, wnd, rect); return; } wxRect drawRect(rect); drawRect.y += m_maxTabHeight + wnd->FromDIP(1); drawRect.height -= m_maxTabHeight; // Mask border not covered by native theme wxRect topDrawRect(rect); topDrawRect.height = drawRect.height; dc.SetPen(wxPen(wnd->GetBackgroundColour(), GetBorderWidth(wnd))); dc.DrawRectangle(topDrawRect); RECT r; wxCopyRectToRECT(drawRect, r); wxUxThemeHandle hTheme(wnd, L"TAB"); ::DrawThemeBackground( hTheme, GetHdcOf(dc.GetTempHDC()), TABP_PANE, 0, &r, NULL); }
int wxAuiMSWTabArt::GetIndentSize() { if ( IsThemed() ) return wxWindow::FromDIP(3, NULL); // This should be 1 but we can't draw into the border from DrawTab else return wxAuiGenericTabArt::GetIndentSize(); }
NS_IMETHODIMP nsGfxRadioControlFrame::BuildDisplayList(nsDisplayListBuilder* aBuilder, const nsRect& aDirtyRect, const nsDisplayListSet& aLists) { nsresult rv = nsFormControlFrame::BuildDisplayList(aBuilder, aDirtyRect, aLists); NS_ENSURE_SUCCESS(rv, rv); if (!IsVisibleForPainting(aBuilder)) return NS_OK; if (IsThemed()) return NS_OK; // The theme will paint the check, if any. bool checked = true; GetCurrentCheckState(&checked); // Get check state from the content model if (!checked) return NS_OK; return aLists.Content()->AppendNewToTop(new (aBuilder) nsDisplayGeneric(aBuilder, this, PaintCheckedRadioButton, "CheckedRadioButton", nsDisplayItem::TYPE_CHECKED_RADIOBUTTON)); }
NS_IMETHODIMP nsCanvasFrame::BuildDisplayList(nsDisplayListBuilder* aBuilder, const nsRect& aDirtyRect, const nsDisplayListSet& aLists) { nsresult rv; if (GetPrevInFlow()) { DisplayOverflowContainers(aBuilder, aDirtyRect, aLists); } // Force a background to be shown. We may have a background propagated to us, // in which case GetStyleBackground wouldn't have the right background // and the code in nsFrame::DisplayBorderBackgroundOutline might not give us // a background. // We don't have any border or outline, and our background draws over // the overflow area, so just add nsDisplayCanvasBackground instead of // calling DisplayBorderBackgroundOutline. if (IsVisibleForPainting(aBuilder)) { nsStyleContext* bgSC; const nsStyleBackground* bg = nullptr; if (!IsThemed() && nsCSSRendering::FindBackground(PresContext(), this, &bgSC)) { bg = bgSC->GetStyleBackground(); } // Create separate items for each background layer. NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(i, bg) { rv = aLists.BorderBackground()->AppendNewToTop( new (aBuilder) nsDisplayCanvasBackground(aBuilder, this, i)); NS_ENSURE_SUCCESS(rv, rv); } }
//------------------------------------------------------------ NS_IMETHODIMP nsGfxCheckboxControlFrame::BuildDisplayList(nsDisplayListBuilder* aBuilder, const nsRect& aDirtyRect, const nsDisplayListSet& aLists) { nsresult rv = nsFormControlFrame::BuildDisplayList(aBuilder, aDirtyRect, aLists); NS_ENSURE_SUCCESS(rv, rv); // Get current checked state through content model. if (!GetCheckboxState() || !IsVisibleForPainting(aBuilder)) return NS_OK; // we're not checked or not visible, nothing to paint. if (IsThemed()) return NS_OK; // No need to paint the checkmark. The theme will do it. // Paint the checkmark if (mCheckButtonFaceStyle) { // This code actually works now; not sure how useful it'll be // (The putpose is to allow the UA stylesheet can substitute its own // checkmark for the default one) const nsStyleBackground* myBackground = mCheckButtonFaceStyle->GetStyleBackground(); if (!myBackground->IsTransparent()) return aLists.Content()->AppendNewToTop(new (aBuilder) nsDisplayGeneric(this, PaintCheckMarkFromStyle, "CheckMarkFromStyle")); } return aLists.Content()->AppendNewToTop(new (aBuilder) nsDisplayCheckMark(this)); }
NS_IMETHODIMP nsComboboxControlFrame::BuildDisplayList(nsDisplayListBuilder* aBuilder, const nsRect& aDirtyRect, const nsDisplayListSet& aLists) { #ifdef NOISY printf("%p paint at (%d, %d, %d, %d)\n", this, aDirtyRect.x, aDirtyRect.y, aDirtyRect.width, aDirtyRect.height); #endif if (aBuilder->IsForEventDelivery()) { // Don't allow children to receive events. // REVIEW: following old GetFrameForPoint nsresult rv = DisplayBorderBackgroundOutline(aBuilder, aLists); NS_ENSURE_SUCCESS(rv, rv); } else { // REVIEW: Our in-flow child frames are inline-level so they will paint in our // content list, so we don't need to mess with layers. nsresult rv = nsBlockFrame::BuildDisplayList(aBuilder, aDirtyRect, aLists); NS_ENSURE_SUCCESS(rv, rv); } nsPresContext *presContext = PresContext(); const nsStyleDisplay *disp = GetStyleDisplay(); if ((!IsThemed(disp) || !presContext->GetTheme()->ThemeDrawsFocusForWidget(presContext, this, disp->mAppearance)) && mDisplayFrame && IsVisibleForPainting(aBuilder)) { nsresult rv = aLists.Content()->AppendNewToTop(new (aBuilder) nsDisplayComboboxFocus(this)); NS_ENSURE_SUCCESS(rv, rv); } return DisplaySelectionOverlay(aBuilder, aLists); }
wxSize wxAuiMSWTabArt::GetTabSize(wxDC& dc, wxWindow* wnd, const wxString& caption, const wxBitmap& bitmap, bool active, int close_button_state, int* x_extent) { if ( !IsThemed() ) return wxAuiGenericTabArt::GetTabSize(dc, wnd, caption, bitmap, active, close_button_state, x_extent); if ( !m_closeBtnSize.IsFullySpecified() ) InitSizes(wnd, dc); wxCoord textWidth, textHeight, tmp; dc.SetFont(wnd->GetFont()); dc.GetTextExtent(caption, &textWidth, &tmp); dc.GetTextExtent("ABCDEFXj", &tmp, &textHeight); wxCoord tabWidth = wxMax(m_tabSize.x, textWidth); wxCoord tabHeight = wxMax(m_tabSize.y, textHeight); // if the close button is showing, add space for it if ( close_button_state != wxAUI_BUTTON_STATE_HIDDEN ) { tabWidth += m_closeBtnSize.x; tabHeight = wxMax(tabHeight, m_closeBtnSize.y); } // if there's a bitmap, add space for it if ( bitmap.IsOk() ) { tabWidth += bitmap.GetWidth() + wnd->FromDIP(3); // bitmap padding tabHeight = wxMax(tabHeight, bitmap.GetHeight() + wnd->FromDIP(2)); } // add padding tabWidth += wnd->FromDIP(12); tabHeight += wnd->FromDIP(3); if ( m_flags & wxAUI_NB_TAB_FIXED_WIDTH ) { tabWidth = m_fixedTabWidth; } else { int minTabWidth = wnd->FromDIP(46); if (tabWidth < minTabWidth) tabWidth = minTabWidth; } *x_extent = tabWidth; if (tabHeight > m_maxTabHeight) m_maxTabHeight = tabHeight; return wxSize(tabWidth, tabHeight); }
int wxAuiMSWTabArt::GetAdditionalBorderSpace(wxWindow* wnd) { if ( IsThemed() ) { return wnd->FromDIP(4, NULL); } else return wxAuiGenericTabArt::GetAdditionalBorderSpace(wnd); }
void CNavPaneWnd::OnThemeChanged() { if (m_hTheme != NULL) XPCloseThemeData(m_hTheme); m_hTheme = NULL; if (IsThemed()) m_hTheme = XPOpenThemeData(m_hWnd, L"TOOLBAR"); Invalidate(); }
int CNavPaneWnd::OnCreate(LPCREATESTRUCT lpCreateStruct) { if (CWnd::OnCreate(lpCreateStruct) == -1) return -1; m_imgClose.Create(IDB_CLOSE, 10, 0, RGB(192, 192, 192)); m_imgSettings.Create(10, 10, ILC_COLOR24 | ILC_MASK, 0, 1); CBitmap bitmap; bitmap.LoadBitmap(IDB_SETTINGS); m_imgSettings.Add(&bitmap, RGB(255, 255, 255)); if (IsThemed()) m_hTheme = XPOpenThemeData(m_hWnd, L"TOOLBAR"); theApp.AddObserver(this); return 0; }
nscoord nsComboboxControlFrame::GetIntrinsicWidth(nsIRenderingContext* aRenderingContext, nsLayoutUtils::IntrinsicWidthType aType) { // get the scrollbar width, we'll use this later nscoord scrollbarWidth = 0; nsPresContext* presContext = PresContext(); if (mListControlFrame) { nsIScrollableFrame* scrollable = do_QueryFrame(mListControlFrame); NS_ASSERTION(scrollable, "List must be a scrollable frame"); scrollbarWidth = scrollable->GetDesiredScrollbarSizes(presContext, aRenderingContext).LeftRight(); } nscoord displayWidth = 0; if (NS_LIKELY(mDisplayFrame)) { displayWidth = nsLayoutUtils::IntrinsicForContainer(aRenderingContext, mDisplayFrame, aType); } if (mDropdownFrame) { nscoord dropdownContentWidth; if (aType == nsLayoutUtils::MIN_WIDTH) { dropdownContentWidth = mDropdownFrame->GetMinWidth(aRenderingContext); } else { NS_ASSERTION(aType == nsLayoutUtils::PREF_WIDTH, "Unexpected type"); dropdownContentWidth = mDropdownFrame->GetPrefWidth(aRenderingContext); } dropdownContentWidth = NSCoordSaturatingSubtract(dropdownContentWidth, scrollbarWidth, nscoord_MAX); displayWidth = PR_MAX(dropdownContentWidth, displayWidth); } // add room for the dropmarker button if there is one if (!IsThemed() || presContext->GetTheme()->ThemeNeedsComboboxDropmarker()) displayWidth += scrollbarWidth; return displayWidth; }
FrameDrawStyle CDwmHelper::DrawType() { if (IsWindows8) { m_DrawType = fdt_Win8; } else if (IsGlass()) { m_DrawType = fdt_Aero; } else if (IsThemed()) { m_DrawType = fdt_Themed; } else { m_DrawType = fdt_Win2k; } return m_DrawType; }
void wxAuiMSWTabArt::DrawBackground(wxDC& dc, wxWindow* wnd, const wxRect& rect) { if ( !IsThemed() ) { wxAuiGenericTabArt::DrawBackground(dc, wnd, rect); return; } int borderHeight = 2; wxRect drawRect = rect; drawRect.height -= borderHeight; // Draw background dc.SetBrush(wxBrush(wnd->GetBackgroundColour())); dc.SetPen(*wxTRANSPARENT_PEN); dc.DrawRectangle(drawRect); // Draw top border drawRect.y = drawRect.height; drawRect.height = borderHeight + 2; drawRect.Inflate(1, 0); RECT r; wxCopyRectToRECT(drawRect, r); wxUxThemeHandle hTheme(wnd, L"TAB"); ::DrawThemeBackground( hTheme, GetHdcOf(dc.GetTempHDC()), TABP_PANE, 0, &r, NULL); }
//------------------------------------------------------------ NS_IMETHODIMP nsGfxCheckboxControlFrame::BuildDisplayList(nsDisplayListBuilder* aBuilder, const nsRect& aDirtyRect, const nsDisplayListSet& aLists) { nsresult rv = nsFormControlFrame::BuildDisplayList(aBuilder, aDirtyRect, aLists); NS_ENSURE_SUCCESS(rv, rv); // Get current checked state through content model. if ((!IsChecked() && !IsIndeterminate()) || !IsVisibleForPainting(aBuilder)) return NS_OK; // we're not checked or not visible, nothing to paint. if (IsThemed()) return NS_OK; // No need to paint the checkmark. The theme will do it. return aLists.Content()->AppendNewToTop(new (aBuilder) nsDisplayGeneric(aBuilder, this, IsIndeterminate() ? PaintIndeterminateMark : PaintCheckMark, "CheckedCheckbox", nsDisplayItem::TYPE_CHECKED_CHECKBOX)); }
/////////////////////////////////////////////////////////////////////////////// // Draw void CXButton::Draw(CDC *pDC, CRect& rect) { //XLISTCTRL_TRACE(_T("in CXButton::Draw: <%s>\n"), m_strText); //TRACERECT(rect); if (m_hTheme == NULL) { // open theme for Button if (ThemeHelper.IsThemeLibAvailable()) { //XLISTCTRL_TRACE(_T("opening theme data ~~~~~\n")); m_hTheme = ThemeHelper.OpenThemeData(m_pParent->m_hWnd, _T("Button")); } } CFont *pFont = m_pParent->GetFont(); CFont *pOldFont = NULL; if (pFont) pOldFont = pDC->SelectObject(pFont); CRect rectButton(rect); m_rect.CopyRect(rectButton); //dc.SetBkMode(TRANSPARENT); pDC->SetBkMode(OPAQUE); DWORD part = BP_PUSHBUTTON; BOOL bIsThemed = IsThemed(m_hTheme); if (bIsThemed) { DWORD state = m_bPressed ? PBS_PRESSED : PBS_NORMAL; if (state == PBS_NORMAL) { if (!m_bEnabled) state = PBS_DISABLED; if (m_bMouseOver) state = PBS_HOT; } ThemeHelper.DrawThemeBackground(m_hTheme, pDC->m_hDC, part, state, &rectButton, NULL); } else { CBrush brBackground(GetSysColor(COLOR_BTNFACE)); pDC->FillRect(&rectButton, &brBackground); // draw pressed button if (m_bPressed) { CBrush brBtnShadow(GetSysColor(COLOR_BTNSHADOW)); pDC->FrameRect(&rectButton, &brBtnShadow); } else // ...else draw non pressed button { UINT uState = DFCS_BUTTONPUSH | (m_bMouseOver ? DFCS_HOT : 0) | ((m_bPressed) ? DFCS_PUSHED : 0); pDC->DrawFrameControl(&rectButton, DFC_BUTTON, uState); } } BOOL bHasText = !m_strText.IsEmpty(); UINT uTextAlignment = DT_CENTER | DT_SINGLELINE | DT_VCENTER | DT_WORDBREAK; // write the button title (if any) if (bHasText) { // draw the button's title - // if button is pressed then "press" title also if (m_bPressed && !bIsThemed) rectButton.OffsetRect(1, 1); if (bIsThemed) { ThemeHelper.DrawThemeText(m_hTheme, pDC->m_hDC, part, m_bEnabled ? PBS_NORMAL : PBS_DISABLED, m_strText, uTextAlignment, 0, &rectButton); } else { pDC->SetBkMode(TRANSPARENT); if (!m_bEnabled) { rectButton.OffsetRect(1, 1); pDC->SetTextColor(::GetSysColor(COLOR_3DHILIGHT)); pDC->DrawText(m_strText, -1, &rectButton, uTextAlignment); rectButton.OffsetRect(-1, -1); pDC->SetTextColor(::GetSysColor(COLOR_3DSHADOW)); pDC->DrawText(m_strText, -1, &rectButton, uTextAlignment); } else { pDC->SetTextColor(::GetSysColor(COLOR_BTNTEXT)); pDC->SetBkColor(::GetSysColor(COLOR_BTNFACE)); pDC->DrawText(m_strText, -1, &rectButton, uTextAlignment); } } } if (pOldFont) pDC->SelectObject(pOldFont); }
NS_IMETHODIMP nsComboboxControlFrame::Reflow(nsPresContext* aPresContext, nsHTMLReflowMetrics& aDesiredSize, const nsHTMLReflowState& aReflowState, nsReflowStatus& aStatus) { // Constraints we try to satisfy: // 1) Default width of button is the vertical scrollbar size // 2) If the width of button is bigger than our width, set width of // button to 0. // 3) Default height of button is height of display area // 4) Width of display area is whatever is left over from our width after // allocating width for the button. // 5) Height of display area is GetHeightOfARow() on the // mListControlFrame. if (!mDisplayFrame || !mButtonFrame || !mDropdownFrame) { NS_ERROR("Why did the frame constructor allow this to happen? Fix it!!"); return NS_ERROR_UNEXPECTED; } // Make sure the displayed text is the same as the selected option, bug 297389. PRInt32 selectedIndex; nsAutoString selectedOptionText; if (!mDroppedDown) { selectedIndex = mListControlFrame->GetSelectedIndex(); } else { // In dropped down mode the "selected index" is the hovered menu item, // we want the last selected item which is |mDisplayedIndex| in this case. selectedIndex = mDisplayedIndex; } if (selectedIndex != -1) { mListControlFrame->GetOptionText(selectedIndex, selectedOptionText); } if (mDisplayedOptionText != selectedOptionText) { RedisplayText(selectedIndex); } // First reflow our dropdown so that we know how tall we should be. ReflowDropdown(aPresContext, aReflowState); // Get the width of the vertical scrollbar. That will be the width of the // dropdown button. nscoord buttonWidth; const nsStyleDisplay *disp = GetStyleDisplay(); if (IsThemed(disp) && !aPresContext->GetTheme()->ThemeNeedsComboboxDropmarker()) { buttonWidth = 0; } else { nsIScrollableFrame* scrollable = do_QueryFrame(mListControlFrame); NS_ASSERTION(scrollable, "List must be a scrollable frame"); buttonWidth = scrollable->GetDesiredScrollbarSizes(PresContext(), aReflowState.rendContext).LeftRight(); if (buttonWidth > aReflowState.ComputedWidth()) { buttonWidth = 0; } } mDisplayWidth = aReflowState.ComputedWidth() - buttonWidth; nsresult rv = nsBlockFrame::Reflow(aPresContext, aDesiredSize, aReflowState, aStatus); NS_ENSURE_SUCCESS(rv, rv); // Now set the correct width and height on our button. The width we need to // set always, the height only if we had an auto height. nsRect buttonRect = mButtonFrame->GetRect(); // If we have a non-intrinsic computed height, our kids should have sized // themselves properly on their own. if (aReflowState.ComputedHeight() == NS_INTRINSICSIZE) { // The display frame is going to be the right height and width at this // point. Use its height as the button height. nsRect displayRect = mDisplayFrame->GetRect(); buttonRect.height = displayRect.height; buttonRect.y = displayRect.y; } #ifdef DEBUG else { nscoord buttonHeight = mButtonFrame->GetSize().height; nscoord displayHeight = mDisplayFrame->GetSize().height; // The button and display area should be equal heights, unless the computed // height on the combobox is too small to fit their borders and padding. NS_ASSERTION(buttonHeight == displayHeight || (aReflowState.ComputedHeight() < buttonHeight && buttonHeight == mButtonFrame->GetUsedBorderAndPadding().TopBottom()) || (aReflowState.ComputedHeight() < displayHeight && displayHeight == mDisplayFrame->GetUsedBorderAndPadding().TopBottom()), "Different heights?"); } #endif if (GetStyleVisibility()->mDirection == NS_STYLE_DIRECTION_RTL) { // Make sure the right edge of the button frame stays where it is now buttonRect.x -= buttonWidth - buttonRect.width; } buttonRect.width = buttonWidth; mButtonFrame->SetRect(buttonRect); return rv; }
NS_IMETHODIMP nsCanvasFrame::BuildDisplayList(nsDisplayListBuilder* aBuilder, const nsRect& aDirtyRect, const nsDisplayListSet& aLists) { nsresult rv; if (GetPrevInFlow()) { DisplayOverflowContainers(aBuilder, aDirtyRect, aLists); } // Force a background to be shown. We may have a background propagated to us, // in which case GetStyleBackground wouldn't have the right background // and the code in nsFrame::DisplayBorderBackgroundOutline might not give us // a background. // We don't have any border or outline, and our background draws over // the overflow area, so just add nsDisplayCanvasBackground instead of // calling DisplayBorderBackgroundOutline. if (IsVisibleForPainting(aBuilder)) { nsStyleContext* bgSC; const nsStyleBackground* bg = nullptr; bool isThemed = IsThemed(); if (!isThemed && nsCSSRendering::FindBackground(PresContext(), this, &bgSC)) { bg = bgSC->GetStyleBackground(); } aLists.BorderBackground()->AppendNewToTop( new (aBuilder) nsDisplayCanvasBackgroundColor(aBuilder, this)); if (isThemed) { return aLists.BorderBackground()->AppendNewToTop( new (aBuilder) nsDisplayCanvasBackgroundImage(aBuilder, this, 0, isThemed, nullptr)); } if (!bg) { return NS_OK; } // Create separate items for each background layer. NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(i, bg) { if (bg->mLayers[i].mImage.IsEmpty()) { continue; } rv = aLists.BorderBackground()->AppendNewToTop( new (aBuilder) nsDisplayCanvasBackgroundImage(aBuilder, this, i, isThemed, bg)); NS_ENSURE_SUCCESS(rv, rv); } } nsIFrame* kid; for (kid = GetFirstPrincipalChild(); kid; kid = kid->GetNextSibling()) { // Put our child into its own pseudo-stack. rv = BuildDisplayListForChild(aBuilder, kid, aDirtyRect, aLists); NS_ENSURE_SUCCESS(rv, rv); } #ifdef DEBUG_CANVAS_FOCUS nsCOMPtr<nsIContent> focusContent; aPresContext->EventStateManager()-> GetFocusedContent(getter_AddRefs(focusContent)); bool hasFocus = false; nsCOMPtr<nsISupports> container; aPresContext->GetContainer(getter_AddRefs(container)); nsCOMPtr<nsIDocShell> docShell(do_QueryInterface(container)); if (docShell) { docShell->GetHasFocus(&hasFocus); printf("%p - nsCanvasFrame::Paint R:%d,%d,%d,%d DR: %d,%d,%d,%d\n", this, mRect.x, mRect.y, mRect.width, mRect.height, aDirtyRect.x, aDirtyRect.y, aDirtyRect.width, aDirtyRect.height); } printf("%p - Focus: %s c: %p DoPaint:%s\n", docShell.get(), hasFocus?"Y":"N", focusContent.get(), mDoPaintFocus?"Y":"N"); #endif if (!mDoPaintFocus) return NS_OK; // Only paint the focus if we're visible if (!GetStyleVisibility()->IsVisible()) return NS_OK; return aLists.Outlines()->AppendNewToTop(new (aBuilder) nsDisplayCanvasFocus(aBuilder, this)); }
/////////////////////////////////////////////////////////////////////////////// // Draw // // nState values are same as XLISTCTRL_NO_CHECKBOX, etc.: // nState = 0 : no checkbox // 1 : unchecked checkbox // 2 : checked checkbox // int CXCheckbox::Draw(CDC* pDC, CRect& rect) { //XLISTCTRL_TRACE(_T("in CXCheckbox::Draw\n")); int nWidth = 0; ASSERT(m_pParent && ::IsWindow(m_pParent->m_hWnd)); if (m_pParent && ::IsWindow(m_pParent->m_hWnd)) { if (m_nCheckedState != XLISTCTRL_NO_CHECKBOX) { m_rect.CopyRect(rect); if (m_rect.Width() > 0) { // center the checkbox int h = XLISTCTRL_CHECKBOX_SIZE; // height and width are the same m_rect.right = m_rect.left + h; m_rect.top = m_rect.top + (m_rect.Height() - h) / 2; m_rect.bottom = m_rect.top + h; if (m_hTheme == NULL) { // open theme for checkbox if (ThemeHelper.IsThemeLibAvailable()) { //XLISTCTRL_TRACE(_T("opening theme data ~~~~~\n")); m_hTheme = ThemeHelper.OpenThemeData(m_pParent->m_hWnd, _T("Button")); } } BOOL bIsThemed = IsThemed(m_hTheme); if (bIsThemed) // user can disable theming for app by // right-clicking on exe, then clicking // on Properties | Compatibility | Disable // visual themes { //XLISTCTRL_TRACE(_T("THEMED ~~~~~\n")); DWORD part = BP_CHECKBOX; DWORD state = (m_nCheckedState == XLISTCTRL_CHECKED_CHECKBOX) ? CBS_CHECKEDNORMAL : CBS_UNCHECKEDNORMAL; if (state == CBS_CHECKEDNORMAL) { if (!m_bEnabled) state = CBS_CHECKEDDISABLED; else if (m_bPressed) state = CBS_CHECKEDPRESSED; else if (m_bMouseOver) state = CBS_CHECKEDHOT; } else { if (!m_bEnabled) state = CBS_UNCHECKEDDISABLED; else if (m_bPressed) state = CBS_UNCHECKEDPRESSED; else if (m_bMouseOver) state = CBS_UNCHECKEDHOT; } ThemeHelper.DrawThemeBackground(m_hTheme, pDC->m_hDC, part, state, &m_rect, NULL); } else { //XLISTCTRL_TRACE(_T("NOT THEMED ~~~~~\n")); // fill rect inside checkbox with white COLORREF oldBackground = pDC->SetBkColor(::GetSysColor(COLOR_WINDOW)); pDC->FillSolidRect(&m_rect, ::GetSysColor(COLOR_WINDOW)); // draw border CBrush brush(RGB(51,102,153)); pDC->FrameRect(&m_rect, &brush); if (m_nCheckedState == XLISTCTRL_CHECKED_CHECKBOX) { CPen pen(PS_SOLID, 1, RGB(51,153,51)); CPen * pOldPen = pDC->SelectObject(&pen); // draw the checkmark int x = m_rect.left + 9; ASSERT(x < m_rect.right); int y = m_rect.top + 3; int i = 0; for (i = 0; i < 4; i++) { pDC->MoveTo(x, y); pDC->LineTo(x, y+3); x--; y++; } for (i = 0; i < 3; i++) { pDC->MoveTo(x, y); pDC->LineTo(x, y+3); x--; y--; } if (pOldPen) pDC->SelectObject(pOldPen); } pDC->SetBkColor(oldBackground); } nWidth = m_rect.Width() + 4; // same as list control } else { // width = 0, do nothing } } } return nWidth; }
//============================================================================= LRESULT CXButtonXP::DefWindowProc(UINT message, WPARAM wParam, LPARAM lParam) //============================================================================= { switch (message) { case WM_GETDLGCODE: { if (lParam) { MSG *pMsg = (MSG *) lParam; if (pMsg) { if ((pMsg->message == WM_KEYDOWN) && (pMsg->wParam == VK_TAB)) { // don't interfere with tab processing return 0; } } } return DLGC_WANTALLKEYS; } break; case WM_KEYDOWN: // ignore repeat messages if key is being held down if (lParam & 0x40000000) return 0; if ((wParam == VK_SPACE) || (wParam == VK_RETURN)) { // convert to left button click SendMessage(WM_LBUTTONDOWN, 0, MAKELPARAM(1, 1)); } break; case WM_KEYUP: if ((wParam == VK_SPACE) || (wParam == VK_RETURN)) { // convert to left button click SendMessage(WM_LBUTTONUP, 0, MAKELPARAM(1, 1)); } break; case WM_LBUTTONUP: { m_bLButtonDown = FALSE; if (m_bSent) { SendMessage(BM_SETSTATE, 0); m_bSent = FALSE; CWnd* pParent = GetParent(); if (pParent != NULL) { ::SendMessage(pParent->m_hWnd, WM_COMMAND, (BN_CLICKED<<16) | this->GetDlgCtrlID(), (LPARAM)this->m_hWnd); } } if (m_bIsToggle) { // if button is toggled and mouse button is released // outside of button, ignore the mouse click and restore // button state CPoint point(GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam)); ClientToScreen(&point); CRect rectButton; GetWindowRect(&rectButton); if (!rectButton.PtInRect(point)) { m_bToggled = !m_bToggled; InvalidateRect(NULL); } } } break; case WM_LBUTTONDOWN: { m_bLButtonDown = TRUE; if (m_bIsToggle) { m_bToggled = !m_bToggled; InvalidateRect(NULL); } } break; case WM_LBUTTONDBLCLK: { if (m_bIsToggle) { // for toggle buttons, treat doubleclick as singleclick SendMessage(BM_SETSTATE, m_bToggled); } else { // SendMessage(BM_SETSTATE, 1); // m_bSent = TRUE; } return 0; } case WM_THEMECHANGED: { if (IsThemed()) { if (m_hTheme) { // when user changes themes, close current theme and re-open ThemeHelper.CloseThemeData(m_hTheme); m_hTheme = NULL; m_bFirstTime = TRUE; } } } break; } return COddButton::DefWindowProc(message, wParam, lParam); }
//============================================================================= void CXButtonXP::DrawItem(LPDRAWITEMSTRUCT lpDIS) //============================================================================= { CDC *pDC = CDC::FromHandle(lpDIS->hDC); CRect rectItem = lpDIS->rcItem; // set up for double buffering CDC memDC; memDC.CreateCompatibleDC(pDC); CBitmap bmp; bmp.CreateCompatibleBitmap(pDC, rectItem.Width(), rectItem.Height()); CBitmap *pOldBitmap = memDC.SelectObject(&bmp); // initialize dc from existing dc memDC.BitBlt(0, 0, rectItem.Width(), rectItem.Height(), pDC, 0, 0, SRCCOPY); memDC.SetBkMode(TRANSPARENT); if (m_bFirstTime) { // open theme for Button m_bFirstTime = FALSE; if (ThemeHelper.IsThemeLibAvailable()) { if (m_hTheme) ThemeHelper.CloseThemeData(m_hTheme); m_hTheme = NULL; if (m_bDrawToolbar) { m_hTheme = ThemeHelper.OpenThemeData(m_hWnd, _T("Toolbar")); } else { m_hTheme = ThemeHelper.OpenThemeData(m_hWnd, _T("Button")); } } SaveParentBackground(); } CFont *pFont = GetParent()->GetFont(); if (pFont) memDC.SelectObject(pFont); // button state // get the button's title CString strTitle = _T(""); GetWindowText(strTitle); BOOL bHasText = !strTitle.IsEmpty(); BOOL bIsFocused = lpDIS->itemState & ODS_FOCUS; BOOL bIsDisabled = lpDIS->itemState & ODS_DISABLED; BOOL bDrawFocusRect = !(lpDIS->itemState & ODS_NOFOCUSRECT); BOOL bIsPressed = lpDIS->itemState & ODS_SELECTED; BOOL bIsDefault = IsDefault(); BOOL bIsThemed = IsThemed(); BOOL bCustomColors = (m_crBackground != XBUTTONXP_NO_COLOR) || (m_crText != XBUTTONXP_NO_COLOR); if (bCustomColors) { bIsThemed = FALSE; } if (m_bIsToggle) { if (m_bLButtonDown && !m_bMouseOverButton) { // left mouse button is down outside button bIsPressed = !m_bToggled; } else { bIsPressed = m_bToggled; } } if (m_bDrawToolbar) { // restore parent window bits memDC.BitBlt(0, 0, m_rectButton.Width(), m_rectButton.Height(), &m_dcParent, 0, 0, SRCCOPY); bIsFocused = FALSE; bIsDefault = FALSE; } if (bIsThemed) { DWORD state = bIsPressed ? PBS_PRESSED : PBS_NORMAL; if (bIsDisabled) { state = PBS_DISABLED; } else if (state == PBS_NORMAL) { if (bIsFocused || bIsDefault) { state = PBS_DEFAULTED; } if (m_bMouseOverButton) state = PBS_HOT; } ThemeHelper.DrawThemeParentBackground(m_hWnd, memDC.m_hDC, &rectItem); ThemeHelper.DrawThemeBackground(m_hTheme, memDC.m_hDC, BP_PUSHBUTTON, state, &rectItem, NULL); } else // not themed { CBrush brBackground; if (m_crBackground == XBUTTONXP_NO_COLOR) brBackground.CreateSolidBrush(GetSysColor(COLOR_BTNFACE)); else brBackground.CreateSolidBrush(m_crBackground); if (!m_bDrawToolbar || bCustomColors) { // fill in background, if custom color or not toolbar CRect rectClient(rectItem); InflateRect(&rectClient, -1, -1); memDC.FillRect(&rectClient, &brBackground); } if (bIsFocused || bIsDefault) { if (!m_bIsToggle || !bIsPressed) { CBrush brush(RGB(0,0,0)); memDC.FrameRect(&rectItem, &brush); } InflateRect(&rectItem, -1, -1); } // draw the traditional pushbutton edge if (bIsPressed) { memDC.DrawEdge(&rectItem, EDGE_SUNKEN, BF_RECT); } else if (!m_bDrawToolbar) { memDC.DrawEdge(&rectItem, EDGE_RAISED, BF_RECT); } } CRect rectDraw = lpDIS->rcItem; // draw the icon DrawIcon(&memDC, bHasText, rectItem, rectDraw, bIsPressed, bIsThemed, bIsDisabled); // draw the button title (if any) if (bHasText) { DrawText(&memDC, strTitle, rectDraw, bIsPressed, bIsThemed, bIsDisabled); } // draw the focus rect if (bIsFocused && bDrawFocusRect) { CRect rectFocus = rectItem; if (m_pDropDownMenu) rectFocus.right = rectFocus.right - MENUBTN_WIDTH + 1; if (!bIsThemed && bIsPressed) rectFocus.OffsetRect(1, 1); rectFocus.InflateRect(-3, -3); memDC.DrawFocusRect(&rectFocus); } if (m_pDropDownMenu) { DrawSplit(&memDC, rectItem, bIsPressed, bIsThemed, bIsDisabled); DrawArrow(&memDC, rectItem, bIsPressed, bIsThemed, bIsDisabled); } // end double buffering pDC->BitBlt(0, 0, rectItem.Width(), rectItem.Height(), &memDC, 0, 0, SRCCOPY); // swap back the original bitmap if (pOldBitmap) memDC.SelectObject(pOldBitmap); if (bmp.GetSafeHandle()) bmp.DeleteObject(); memDC.DeleteDC(); }
void wxAuiMSWTabArt::DrawTab(wxDC& dc, wxWindow* wnd, const wxAuiNotebookPage& page, const wxRect& in_rect, int close_button_state, wxRect* out_tab_rect, wxRect* out_button_rect, int* x_extent) { if ( !IsThemed() ) { wxAuiGenericTabArt::DrawTab(dc, wnd, page, in_rect, close_button_state, out_tab_rect, out_button_rect, x_extent); return; } if ( !m_closeBtnSize.IsFullySpecified() ) InitSizes(wnd, dc); // figure out the size of the tab wxSize tabSize = GetTabSize(dc, wnd, page.caption, page.bitmap, page.active, close_button_state, x_extent); wxCoord tabHeight = tabSize.y; wxCoord tabWidth = tabSize.x; wxCoord tabX = in_rect.x; wxCoord tabY = 0; if (!page.active) { tabY += wnd->FromDIP(2); tabHeight -= wnd->FromDIP(2); } else { tabX -= wnd->FromDIP(2); tabWidth += wnd->FromDIP(4); tabHeight += 2; } int clipWidth = tabWidth; if ( tabX + clipWidth > in_rect.x + in_rect.width ) clipWidth = (in_rect.x + in_rect.width) - tabX; dc.SetClippingRegion(tabX - wnd->FromDIP(2), tabY, clipWidth + wnd->FromDIP(4), tabHeight); // draw tab wxRect tabRect(tabX, tabY, tabWidth, tabHeight); int tabState; if ( page.active ) tabState = TIS_SELECTED; else if ( page.hover ) tabState = TIS_HOT; else tabState = TIS_NORMAL; wxUxThemeHandle hTabTheme(wnd, L"Tab"); RECT tabR; wxCopyRectToRECT(tabRect, tabR); ::DrawThemeBackground(hTabTheme, GetHdcOf(dc.GetTempHDC()), TABP_TABITEM, tabState, &tabR, NULL); // Apparently, in at least some Windows 10 installations the call above // does not draw the left edge of the first tab and it needs to be drawn // separately, or it wouldn't be drawn at all. if ( tabX == GetIndentSize() ) { ::DrawThemeBackground ( hTabTheme, GetHdcOf(dc.GetTempHDC()), TABP_TABITEMLEFTEDGE, tabState, &tabR, NULL ); } wxRect textRect = tabRect; if ( !page.active ) textRect.Offset(0, wnd->FromDIP(1)); if ( close_button_state != wxAUI_BUTTON_STATE_HIDDEN ) textRect.width -= m_closeBtnSize.x + wnd->FromDIP(3); dc.SetFont(wnd->GetFont()); dc.DrawLabel(page.caption, page.bitmap, textRect, wxALIGN_CENTRE); // draw focus rectangle if ( page.active && (wnd->FindFocus() == wnd) ) { wxRect focusRect = tabRect; focusRect.Deflate(wnd->FromDIP(2)); wxRendererNative::Get().DrawFocusRect(wnd, dc, focusRect, 0); } // draw close button if ( close_button_state != wxAUI_BUTTON_STATE_HIDDEN ) { wxUxThemeHandle hToolTipTheme(wnd, L"TOOLTIP"); int btnState; if ( close_button_state == wxAUI_BUTTON_STATE_HOVER ) btnState = TTCS_HOT; else if ( close_button_state == wxAUI_BUTTON_STATE_PRESSED ) btnState = TTCS_PRESSED; else btnState = TTCS_NORMAL; int offsetY = tabY; if ( wxGetWinVersion() < wxWinVersion_Vista ) offsetY++; // WinXP theme needs a little more padding wxRect rect(tabX + tabWidth - m_closeBtnSize.x - wnd->FromDIP(4), offsetY + (tabHeight / 2) - (m_closeBtnSize.y / 2), m_closeBtnSize.x, m_closeBtnSize.y); RECT btnR; wxCopyRectToRECT(rect, btnR); ::DrawThemeBackground(hToolTipTheme, GetHdcOf(dc.GetTempHDC()), TTP_CLOSE, btnState, &btnR, NULL); if ( out_button_rect ) *out_button_rect = rect; } *out_tab_rect = wxRect(tabX, tabY, tabWidth, tabHeight); dc.DestroyClippingRegion(); }
void wxAuiMSWTabArt::DrawButton(wxDC& dc, wxWindow* wnd, const wxRect& in_rect, int bitmap_id, int button_state, int orientation, wxRect* out_rect) { if ( !IsThemed() ) { wxAuiGenericTabArt::DrawButton(dc, wnd, in_rect, bitmap_id, button_state, orientation, out_rect); return; } const wchar_t* themeId = NULL; int part = 0; switch (bitmap_id) { case wxAUI_BUTTON_CLOSE: themeId = L"Window"; part = WP_CLOSEBUTTON; break; case wxAUI_BUTTON_LEFT: themeId = L"Spin"; part = SPNP_DOWNHORZ; break; case wxAUI_BUTTON_RIGHT: themeId = L"Spin"; part = SPNP_UPHORZ; break; case wxAUI_BUTTON_WINDOWLIST: themeId = L"Combobox"; part = CP_DROPDOWNBUTTON; break; } wxRect rect = in_rect; if ( orientation == wxLEFT ) { rect.SetX(in_rect.x); rect.SetY(((in_rect.y + in_rect.height) / 2) - (m_closeBtnSize.GetHeight() / 2)); rect.SetWidth(m_closeBtnSize.GetWidth()); rect.SetHeight(m_closeBtnSize.GetHeight()); } else { rect = wxRect(in_rect.x + in_rect.width - m_closeBtnSize.GetWidth(), ((in_rect.y + in_rect.height) / 2) - (m_closeBtnSize.GetHeight() / 2), m_closeBtnSize.GetWidth(), m_closeBtnSize.GetHeight()); } if ( bitmap_id == wxAUI_BUTTON_LEFT || bitmap_id == wxAUI_BUTTON_RIGHT ) { rect.y = in_rect.y; rect.height = in_rect.height - wnd->FromDIP(7); } dc.SetPen(*wxTRANSPARENT_PEN); dc.SetBrush(wxBrush(m_baseColour)); dc.DrawRectangle(rect); int btnState; if ( button_state == wxAUI_BUTTON_STATE_DISABLED ) btnState = TTCS_PRESSED + 1; else if ( button_state == wxAUI_BUTTON_STATE_HOVER ) btnState = TTCS_HOT; else if ( button_state == wxAUI_BUTTON_STATE_PRESSED ) btnState = TTCS_PRESSED; else btnState = TTCS_NORMAL; wxUxThemeHandle hTheme(wnd, themeId); wxRect btnRect(rect); btnRect.width -= wnd->FromDIP(1); RECT btnR; wxCopyRectToRECT(btnRect, btnR); ::DrawThemeBackground(hTheme, GetHdcOf(dc.GetTempHDC()), part, btnState, &btnR, NULL); if ( out_rect ) *out_rect = rect; }