You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
882 lines
18 KiB
C++
882 lines
18 KiB
C++
2 years ago
|
// XTButton.cpp : implementation of the CXTPButton class.
|
||
|
//
|
||
|
// This file is a part of the XTREME CONTROLS MFC class library.
|
||
|
// (c)1998-2012 Codejock Software, All Rights Reserved.
|
||
|
//
|
||
|
// THIS SOURCE FILE IS THE PROPERTY OF CODEJOCK SOFTWARE AND IS NOT TO BE
|
||
|
// RE-DISTRIBUTED BY ANY MEANS WHATSOEVER WITHOUT THE EXPRESSED WRITTEN
|
||
|
// CONSENT OF CODEJOCK SOFTWARE.
|
||
|
//
|
||
|
// THIS SOURCE CODE CAN ONLY BE USED UNDER THE TERMS AND CONDITIONS OUTLINED
|
||
|
// IN THE XTREME TOOLKIT PRO LICENSE AGREEMENT. CODEJOCK SOFTWARE GRANTS TO
|
||
|
// YOU (ONE SOFTWARE DEVELOPER) THE LIMITED RIGHT TO USE THIS SOFTWARE ON A
|
||
|
// SINGLE COMPUTER.
|
||
|
//
|
||
|
// CONTACT INFORMATION:
|
||
|
// support@codejock.com
|
||
|
// http://www.codejock.com
|
||
|
//
|
||
|
/////////////////////////////////////////////////////////////////////////////
|
||
|
|
||
|
#include "stdafx.h"
|
||
|
|
||
|
#include "Common/XTPDrawHelpers.h"
|
||
|
#include "Common/XTPImageManager.h"
|
||
|
#include "Common/XTPMarkupRender.h"
|
||
|
#include "Common/XTPToolTipContext.h"
|
||
|
#include "Common/XTPMaskEditT.h"
|
||
|
#include "Common/XTPWinThemeWrapper.h"
|
||
|
#include "Common/XTPColorManager.h"
|
||
|
|
||
|
#include "../Util/XTPControlTheme.h"
|
||
|
|
||
|
#include "../Defines.h"
|
||
|
#include "XTPButton.h"
|
||
|
#include "XTPButtonTheme.h"
|
||
|
#include "../Edit/XTPEdit.h"
|
||
|
|
||
|
#ifdef _DEBUG
|
||
|
#define new DEBUG_NEW
|
||
|
#undef THIS_FILE
|
||
|
static char THIS_FILE[] = __FILE__;
|
||
|
#endif
|
||
|
|
||
|
#ifndef WM_UPDATEUISTATE
|
||
|
#define WM_UPDATEUISTATE 0x0128
|
||
|
#endif
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////////////
|
||
|
// CXTPButton
|
||
|
/////////////////////////////////////////////////////////////////////////////
|
||
|
|
||
|
#ifndef _XTP_ACTIVEX_BUTTON
|
||
|
IMPLEMENT_DYNAMIC(CXTPButton, CXTPButtonBase)
|
||
|
#endif
|
||
|
|
||
|
CXTPButton::CXTPButton()
|
||
|
: m_pTheme(NULL)
|
||
|
{
|
||
|
m_bHot = FALSE;
|
||
|
m_bPushed = FALSE;
|
||
|
|
||
|
m_bChecked = FALSE;
|
||
|
|
||
|
m_bFlatStyle = FALSE;
|
||
|
m_bUseVisualStyle = TRUE;
|
||
|
|
||
|
m_bEnableMarkup = FALSE;
|
||
|
m_pMarkupContext = NULL;
|
||
|
m_pUIElement = NULL;
|
||
|
|
||
|
m_nPushButtonStyle = 0;
|
||
|
|
||
|
m_nBorderGap = 4;
|
||
|
m_nImageGap = 3;
|
||
|
|
||
|
m_pIcon = 0;
|
||
|
|
||
|
m_nImageAlignment = BS_VCENTER | BS_CENTER;
|
||
|
m_nTextImageRelation = xtpButtonImageBeforeText;
|
||
|
|
||
|
m_nBorderStyle = 0;
|
||
|
m_bShowFocus = TRUE;
|
||
|
|
||
|
m_hWndBuddy = 0;
|
||
|
|
||
|
m_pToolTipContext = new CXTPToolTipContext();
|
||
|
|
||
|
VERIFY(SetTheme(xtpControlThemeDefault));
|
||
|
}
|
||
|
|
||
|
CXTPButton::~CXTPButton()
|
||
|
{
|
||
|
CMDTARGET_RELEASE(m_pTheme);
|
||
|
|
||
|
XTPMarkupReleaseElement(m_pUIElement);
|
||
|
XTPMarkupReleaseContext(m_pMarkupContext);
|
||
|
|
||
|
CMDTARGET_RELEASE(m_pIcon);
|
||
|
CMDTARGET_RELEASE(m_pToolTipContext);
|
||
|
}
|
||
|
|
||
|
BEGIN_MESSAGE_MAP(CXTPButton, CXTPButtonBase)
|
||
|
//{{AFX_MSG_MAP(CXTPButton)
|
||
|
ON_WM_ERASEBKGND()
|
||
|
ON_WM_MOUSEMOVE()
|
||
|
ON_WM_SETFOCUS()
|
||
|
ON_WM_KILLFOCUS()
|
||
|
ON_WM_LBUTTONDOWN()
|
||
|
ON_WM_LBUTTONUP()
|
||
|
ON_MESSAGE(WM_PRINTCLIENT, OnPrintClient)
|
||
|
ON_WM_CHAR()
|
||
|
ON_WM_KEYDOWN()
|
||
|
ON_MESSAGE(WM_GETDLGCODE, OnGetDlgCode)
|
||
|
//}}AFX_MSG_MAP
|
||
|
#ifndef _XTP_ACTIVEX_BUTTON
|
||
|
ON_WM_PAINT()
|
||
|
#endif
|
||
|
ON_MESSAGE_VOID(WM_MOUSELEAVE, OnMouseLeave)
|
||
|
ON_MESSAGE(BM_SETSTYLE, OnDefaultAndInvalidate)
|
||
|
ON_MESSAGE(BM_SETCHECK, OnDefaultAndInvalidate)
|
||
|
ON_MESSAGE(WM_CAPTURECHANGED, OnCaptureChanged)
|
||
|
ON_MESSAGE_VOID(WM_ENABLE, OnInvalidate)
|
||
|
ON_MESSAGE(WM_UPDATEUISTATE, OnUpdateUIState)
|
||
|
ON_MESSAGE(BM_SETSTATE, OnSetState)
|
||
|
ON_MESSAGE(WM_SETTEXT, OnSetText)
|
||
|
ON_MESSAGE(WM_XTP_SETCONTROLTHEME, OnSetTheme)
|
||
|
END_MESSAGE_MAP()
|
||
|
|
||
|
void CXTPButton::OnMouseMove(UINT nFlags, CPoint point)
|
||
|
{
|
||
|
if (GetButtonStyle() == BS_GROUPBOX)
|
||
|
return;
|
||
|
|
||
|
CXTPButtonBase::OnMouseMove(nFlags, point);
|
||
|
|
||
|
CRect rc = GetButtonRect();
|
||
|
|
||
|
BOOL bHot = rc.PtInRect(point);
|
||
|
if (bHot != m_bHot)
|
||
|
{
|
||
|
m_bHot = bHot;
|
||
|
RedrawButton();
|
||
|
|
||
|
if (m_bHot)
|
||
|
{
|
||
|
TRACKMOUSEEVENT tme = {sizeof(TRACKMOUSEEVENT), TME_LEAVE, m_hWnd, HOVER_DEFAULT};
|
||
|
_TrackMouseEvent(&tme);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnMouseLeave()
|
||
|
{
|
||
|
OnMouseMove(0, CPoint(-1, -1));
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnLButtonDown(UINT nFlags, CPoint point)
|
||
|
{
|
||
|
if (m_nPushButtonStyle == xtpButtonSplitDropDown)
|
||
|
{
|
||
|
CRect rcDropDown(GetButtonRect());
|
||
|
rcDropDown.left = rcDropDown.right - 16 - GetBorderGap();
|
||
|
|
||
|
if (rcDropDown.PtInRect(point))
|
||
|
{
|
||
|
DoDropDown();
|
||
|
return;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
CXTPButtonBase::OnLButtonDown(nFlags, point);
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnLButtonUp(UINT nFlags, CPoint point)
|
||
|
{
|
||
|
CXTPButtonBase::OnLButtonUp(nFlags, point);
|
||
|
}
|
||
|
|
||
|
LRESULT CXTPButton::OnSetState(WPARAM wParam, LPARAM /*lParam*/)
|
||
|
{
|
||
|
BOOL bVisible = GetStyle() & WS_VISIBLE;
|
||
|
if (bVisible) ModifyStyle(WS_VISIBLE, 0);
|
||
|
Default();
|
||
|
if (bVisible) ModifyStyle(0, WS_VISIBLE);
|
||
|
|
||
|
if (m_bPushed == 2)
|
||
|
return 0;
|
||
|
|
||
|
m_bPushed = (wParam != 0);
|
||
|
RedrawButton();
|
||
|
|
||
|
if (m_bPushed && IsDropDownStyle() && IsPushButton() && (m_nPushButtonStyle != xtpButtonSplitDropDown))
|
||
|
{
|
||
|
DoDropDown();
|
||
|
}
|
||
|
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
CRect CXTPButton::GetButtonRect()
|
||
|
{
|
||
|
CXTPClientRect rc(this);
|
||
|
|
||
|
if (m_hWndBuddy)
|
||
|
{
|
||
|
CXTPEdit* pEditBuddy = DYNAMIC_DOWNCAST(CXTPEdit, CWnd::FromHandlePermanent(m_hWndBuddy));
|
||
|
if (pEditBuddy) pEditBuddy->AdjustBuddyRect(this, rc, UDS_ALIGNRIGHT);
|
||
|
}
|
||
|
|
||
|
return rc;
|
||
|
}
|
||
|
|
||
|
void CXTPButton::DoDropDown()
|
||
|
{
|
||
|
m_bPushed = 2;
|
||
|
RedrawButton();
|
||
|
|
||
|
OnDropDown();
|
||
|
|
||
|
m_bPushed = 0;
|
||
|
RedrawButton();
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnChar(UINT nChar, UINT nRepCnt, UINT nFlags)
|
||
|
{
|
||
|
if (IsDropDownStyle() && (nChar == VK_SPACE))
|
||
|
{
|
||
|
DoDropDown();
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
if ((m_nPushButtonStyle == xtpButtonDropDown || m_nPushButtonStyle == xtpButtonDropDownRight) && (nChar == VK_RETURN))
|
||
|
{
|
||
|
DoDropDown();
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
CXTPButtonBase::OnChar(nChar, nRepCnt, nFlags);
|
||
|
}
|
||
|
|
||
|
LRESULT CXTPButton::OnGetDlgCode(WPARAM wParam, LPARAM lParam)
|
||
|
{
|
||
|
LRESULT lCode = CXTPButtonBase::OnGetDlgCode();
|
||
|
|
||
|
if (IsDropDownStyle() && lParam && ((LPMSG)lParam)->message == WM_CHAR && wParam == VK_SPACE)
|
||
|
{
|
||
|
lCode |= DLGC_WANTCHARS;
|
||
|
}
|
||
|
|
||
|
if ((m_nPushButtonStyle == xtpButtonDropDown || m_nPushButtonStyle == xtpButtonDropDownRight)
|
||
|
&& lParam && (((LPMSG)lParam)->message == WM_KEYDOWN || ((LPMSG)lParam)->message == WM_CHAR) && wParam == VK_RETURN)
|
||
|
{
|
||
|
lCode |= DLGC_WANTALLKEYS;
|
||
|
}
|
||
|
|
||
|
return lCode;
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags)
|
||
|
{
|
||
|
if (nChar == VK_SPACE && IsDropDownStyle())
|
||
|
return;
|
||
|
|
||
|
if (nChar == VK_RETURN && (m_nPushButtonStyle == xtpButtonDropDown || m_nPushButtonStyle == xtpButtonDropDownNoGlyph || m_nPushButtonStyle == xtpButtonDropDownRight))
|
||
|
{
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
CXTPButtonBase::OnKeyDown(nChar, nRepCnt, nFlags);
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnDropDown()
|
||
|
{
|
||
|
GetParent()->SendMessage(WM_COMMAND,
|
||
|
(WPARAM)MAKELONG(::GetDlgCtrlID(GetSafeHwnd()), CBN_DROPDOWN),
|
||
|
(LPARAM)GetSafeHwnd());
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnSetFocus(CWnd* pOldWnd)
|
||
|
{
|
||
|
CXTPButtonBase::OnSetFocus(pOldWnd);
|
||
|
RedrawButton(TRUE);
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnKillFocus(CWnd* pNewWnd)
|
||
|
{
|
||
|
CXTPButtonBase::OnKillFocus(pNewWnd);
|
||
|
RedrawButton(TRUE);
|
||
|
}
|
||
|
|
||
|
LRESULT CXTPButton::OnCaptureChanged(WPARAM wParam, LPARAM lParam)
|
||
|
{
|
||
|
return OnDefaultAndInvalidate(wParam, lParam);
|
||
|
}
|
||
|
|
||
|
LRESULT CXTPButton::OnDefaultAndInvalidate(WPARAM, LPARAM)
|
||
|
{
|
||
|
LRESULT lResult = Default();
|
||
|
RedrawButton(TRUE);
|
||
|
|
||
|
return lResult;
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnInvalidate()
|
||
|
{
|
||
|
RedrawButton(TRUE);
|
||
|
}
|
||
|
|
||
|
LRESULT CXTPButton::OnPrintClient(WPARAM wParam, LPARAM lParam)
|
||
|
{
|
||
|
if ((lParam & PRF_CLIENT) == 0)
|
||
|
return Default();
|
||
|
|
||
|
CDC* pDC = CDC::FromHandle((HDC)wParam);
|
||
|
if (pDC) OnDraw(pDC);
|
||
|
return 1;
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnPaint()
|
||
|
{
|
||
|
CPaintDC dcPaint(this);
|
||
|
OnDraw(&dcPaint);
|
||
|
}
|
||
|
|
||
|
void CXTPButton::OnDraw(CDC* pDC)
|
||
|
{
|
||
|
if ((GetButtonStyle() == BS_GROUPBOX))
|
||
|
{
|
||
|
CFont* pOldFont = pDC->SelectObject(CWnd::GetFont());
|
||
|
pDC->SetBkColor(GetSysColor(COLOR_3DFACE));
|
||
|
pDC->SetBkMode(TRANSPARENT);
|
||
|
|
||
|
DoDraw(pDC);
|
||
|
|
||
|
pDC->SelectObject(pOldFont);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
CXTPClientRect rc(this);
|
||
|
CXTPBufferDC memDC(*pDC, rc);
|
||
|
|
||
|
HBRUSH hBrush = (HBRUSH)GetParent()->SendMessage(WM_CTLCOLORBTN, (WPARAM)memDC.GetSafeHdc(), (LPARAM)GetSafeHwnd());
|
||
|
if (hBrush)
|
||
|
{
|
||
|
::FillRect(memDC.GetSafeHdc(), rc, hBrush);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
memDC.FillSolidRect(rc, GetSysColor(COLOR_3DFACE));
|
||
|
}
|
||
|
|
||
|
CFont* pOldFont = memDC.SelectObject(CWnd::GetFont());
|
||
|
memDC.SetBkMode(TRANSPARENT);
|
||
|
|
||
|
DoDraw(&memDC);
|
||
|
|
||
|
memDC.SelectObject(pOldFont);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void CXTPButtonTheme::DrawButton(CDC* pDC, CXTPButton* pButton)
|
||
|
{
|
||
|
if (pButton->IsPushButton())
|
||
|
{
|
||
|
DrawButtonBackground(pDC, pButton);
|
||
|
|
||
|
DrawPushButtonText(pDC, pButton);
|
||
|
DrawPushButtonIcon(pDC, pButton);
|
||
|
|
||
|
if (pButton->IsDropDownStyle() && pButton->GetPushButtonStyle() != xtpButtonDropDownNoGlyph)
|
||
|
{
|
||
|
DrawPushButtonDropDown(pDC, pButton);
|
||
|
}
|
||
|
|
||
|
if (::GetFocus() == pButton->m_hWnd && pButton->GetShowFocus())
|
||
|
{
|
||
|
DrawFocusRect(pDC, pButton);
|
||
|
}
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
switch (pButton->GetButtonStyle())
|
||
|
{
|
||
|
case BS_RADIOBUTTON:
|
||
|
case BS_AUTORADIOBUTTON:
|
||
|
DrawRadioButtonMark(pDC, pButton);
|
||
|
DrawButtonText(pDC, pButton);
|
||
|
break;
|
||
|
|
||
|
case BS_3STATE:
|
||
|
case BS_AUTO3STATE:
|
||
|
case BS_CHECKBOX:
|
||
|
case BS_AUTOCHECKBOX:
|
||
|
DrawCheckBoxMark(pDC, pButton);
|
||
|
DrawButtonText(pDC, pButton);
|
||
|
break;
|
||
|
|
||
|
case BS_GROUPBOX:
|
||
|
if (pButton->GetBorderStyle() != 2)
|
||
|
{
|
||
|
DrawGroupBox(pDC, pButton);
|
||
|
DrawButtonText(pDC, pButton);
|
||
|
}
|
||
|
break;
|
||
|
|
||
|
default:
|
||
|
TRACE(_T("Warning: unkown style"));
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void CXTPButton::DoDraw(CDC* pDC)
|
||
|
{
|
||
|
if (m_hWndBuddy)
|
||
|
{
|
||
|
CXTPEdit* pEditBuddy = DYNAMIC_DOWNCAST(CXTPEdit, CWnd::FromHandlePermanent(m_hWndBuddy));
|
||
|
if (pEditBuddy) pEditBuddy->DrawBuddyBorders(this, pDC, CXTPClientRect(this), UDS_ALIGNRIGHT);
|
||
|
}
|
||
|
|
||
|
m_pTheme->DrawButton(pDC, this);
|
||
|
}
|
||
|
|
||
|
LRESULT CXTPButton::OnUpdateUIState(WPARAM wParam, LPARAM lParam)
|
||
|
{
|
||
|
LRESULT lResult = ::DefWindowProc(m_hWnd, WM_UPDATEUISTATE, wParam, lParam);
|
||
|
RedrawButton();
|
||
|
|
||
|
return lResult;
|
||
|
}
|
||
|
|
||
|
LRESULT CXTPButton::OnSetText(WPARAM wParam, LPARAM lParam)
|
||
|
{
|
||
|
BOOL bVisible = GetStyle() & WS_VISIBLE;
|
||
|
if (bVisible) ModifyStyle(WS_VISIBLE, 0);
|
||
|
|
||
|
LRESULT lResult = DefWindowProc(WM_SETTEXT, wParam, lParam);
|
||
|
|
||
|
if (bVisible) ModifyStyle(0, WS_VISIBLE);
|
||
|
|
||
|
|
||
|
InternalTextChanged();
|
||
|
RedrawButton();
|
||
|
|
||
|
return lResult;
|
||
|
}
|
||
|
|
||
|
BOOL CXTPButton::OnEraseBkgnd(CDC* /*pDC*/)
|
||
|
{
|
||
|
return TRUE;
|
||
|
}
|
||
|
|
||
|
//////////////////////////////////////////////////////////////////////////
|
||
|
|
||
|
COLORREF CXTPButton::GetButtonTextColor()
|
||
|
{
|
||
|
return GetSysColor(COLOR_BTNTEXT);
|
||
|
}
|
||
|
|
||
|
COLORREF CXTPButton::GetButtonBackColor()
|
||
|
{
|
||
|
return GetSysColor(COLOR_BTNFACE);
|
||
|
}
|
||
|
|
||
|
BYTE CXTPButton::GetButtonStyle() const
|
||
|
{
|
||
|
BYTE bStyle = BYTE(GetStyle() & 0xF);
|
||
|
return bStyle;
|
||
|
}
|
||
|
|
||
|
|
||
|
CSize CXTPButton::GetImageSize()
|
||
|
{
|
||
|
if (m_pIcon)
|
||
|
return CSize(m_pIcon->GetWidth(), m_pIcon->GetHeight());
|
||
|
|
||
|
return CSize(0, 0);
|
||
|
}
|
||
|
|
||
|
void CXTPButton::DrawImage(CDC* pDC, CRect rc)
|
||
|
{
|
||
|
CXTPImageManagerIcon* pIcon = GetIcon();
|
||
|
if (pIcon)
|
||
|
{
|
||
|
BOOL bSelected = GetChecked() || IsPushed();
|
||
|
|
||
|
if (!IsWindowEnabled())
|
||
|
{
|
||
|
pIcon->Draw(pDC, rc.TopLeft(), pIcon->GetDisabledIcon(), rc.Size());
|
||
|
}
|
||
|
else if (IsHighlighted() || bSelected)
|
||
|
{
|
||
|
pIcon->Draw(pDC, rc.TopLeft(), GetChecked() ? pIcon->GetCheckedIcon() :
|
||
|
IsPushed() ? pIcon->GetPressedIcon() : pIcon->GetHotIcon(), rc.Size());
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
pIcon->Draw(pDC, rc.TopLeft(), pIcon->GetIcon(), rc.Size());
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
BOOL CXTPButton::OnWndMsg(UINT message, WPARAM wParam, LPARAM lParam, LRESULT* pResult)
|
||
|
{
|
||
|
if (message == WM_SETTINGCHANGE || message == WM_SYSCOLORCHANGE)
|
||
|
{
|
||
|
RefreshMetrics();
|
||
|
}
|
||
|
|
||
|
if (m_pUIElement)
|
||
|
{
|
||
|
if (XTPMarkupRelayMessage(m_pUIElement, message, wParam, lParam, pResult))
|
||
|
return TRUE;
|
||
|
}
|
||
|
|
||
|
if (m_pToolTipContext)
|
||
|
{
|
||
|
m_pToolTipContext->FilterToolTipMessage(this, message, wParam, lParam);
|
||
|
}
|
||
|
|
||
|
return CXTPButtonBase::OnWndMsg(message, wParam, lParam, pResult);
|
||
|
}
|
||
|
|
||
|
int CXTPButton::GetTextAlignment() const
|
||
|
{
|
||
|
DWORD bHorz;
|
||
|
DWORD bVert;
|
||
|
|
||
|
DWORD dwStyle = GetStyle();
|
||
|
|
||
|
bHorz = dwStyle & (BS_LEFT | BS_RIGHT | BS_CENTER);
|
||
|
bVert = dwStyle & (BS_TOP | BS_BOTTOM | BS_VCENTER);
|
||
|
|
||
|
if (!bHorz || !bVert)
|
||
|
{
|
||
|
if (IsPushButton())
|
||
|
{
|
||
|
if (!bHorz)
|
||
|
bHorz = BS_CENTER;
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
if (!bHorz)
|
||
|
bHorz = BS_LEFT;
|
||
|
}
|
||
|
|
||
|
if (!bVert)
|
||
|
bVert = BS_VCENTER;
|
||
|
}
|
||
|
|
||
|
return bHorz | bVert;
|
||
|
}
|
||
|
|
||
|
CSize CXTPButton::GetGlyphSize(BOOL bCheckBox)
|
||
|
{
|
||
|
CRect rcButton = GetButtonRect();
|
||
|
CSize sz(13, 13);
|
||
|
|
||
|
if (m_bUseVisualStyle && m_pTheme->m_themeButton->IsAppThemed())
|
||
|
{
|
||
|
m_pTheme->m_themeButton->GetThemePartSize(NULL,
|
||
|
bCheckBox ? BP_CHECKBOX : BP_RADIOBUTTON,
|
||
|
1, rcButton, TS_TRUE, &sz);
|
||
|
}
|
||
|
|
||
|
return sz;
|
||
|
}
|
||
|
|
||
|
void CXTPButton::InternalTextChanged()
|
||
|
{
|
||
|
if (m_pMarkupContext)
|
||
|
{
|
||
|
XTPMarkupReleaseElement(m_pUIElement);
|
||
|
m_pUIElement = XTPMarkupParseText(m_pMarkupContext, GetButtonText());
|
||
|
}
|
||
|
}
|
||
|
|
||
|
CString CXTPButton::GetButtonText()
|
||
|
{
|
||
|
CString str;
|
||
|
if (m_hWnd) GetWindowText(str);
|
||
|
return str;
|
||
|
}
|
||
|
|
||
|
void CXTPButton::EnableMarkup(BOOL bEnableMarkup)
|
||
|
{
|
||
|
m_bEnableMarkup = bEnableMarkup;
|
||
|
|
||
|
XTPMarkupReleaseElement(m_pUIElement);
|
||
|
XTPMarkupReleaseContext(m_pMarkupContext);
|
||
|
|
||
|
if (m_bEnableMarkup)
|
||
|
{
|
||
|
m_pMarkupContext = XTPMarkupCreateContext(m_hWnd);
|
||
|
}
|
||
|
|
||
|
InternalTextChanged();
|
||
|
}
|
||
|
|
||
|
BOOL CXTPButton::IsPushButton() const
|
||
|
{
|
||
|
DWORD dwStyle = GetStyle();
|
||
|
|
||
|
switch (GetButtonStyle())
|
||
|
{
|
||
|
case LOBYTE(BS_PUSHBUTTON):
|
||
|
case LOBYTE(BS_DEFPUSHBUTTON):
|
||
|
case LOBYTE(BS_OWNERDRAW):
|
||
|
return TRUE;
|
||
|
|
||
|
default:
|
||
|
if ((dwStyle & BS_PUSHLIKE) == BS_PUSHLIKE)
|
||
|
return TRUE;
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
return FALSE;
|
||
|
}
|
||
|
|
||
|
void CXTPButton::SetTheme(CXTPButtonTheme* pPaintManager)
|
||
|
{
|
||
|
CMDTARGET_RELEASE(m_pTheme);
|
||
|
m_pTheme = pPaintManager;
|
||
|
|
||
|
m_bUseVisualStyle = pPaintManager->GetThemeStyle() == xtpControlThemeDefault;
|
||
|
|
||
|
if (m_pTheme)
|
||
|
{
|
||
|
m_pTheme->RefreshMetrics(this);
|
||
|
}
|
||
|
|
||
|
if (::IsWindow(m_hWnd))
|
||
|
{
|
||
|
RedrawButton();
|
||
|
}
|
||
|
}
|
||
|
|
||
|
LRESULT CXTPButton::OnSetTheme(WPARAM wParam, LPARAM /*lParam*/)
|
||
|
{
|
||
|
XTPControlTheme eTheme = (XTPControlTheme)wParam;
|
||
|
|
||
|
SetTheme(eTheme);
|
||
|
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
void CXTPButton::RefreshMetrics()
|
||
|
{
|
||
|
if (m_pTheme)
|
||
|
m_pTheme->RefreshMetrics(this);
|
||
|
|
||
|
if (::IsWindow(m_hWnd))
|
||
|
RedrawButton();
|
||
|
}
|
||
|
|
||
|
BOOL CXTPButton::SetTheme(XTPControlTheme eTheme)
|
||
|
{
|
||
|
CMDTARGET_RELEASE(m_pTheme);
|
||
|
|
||
|
switch (eTheme)
|
||
|
{
|
||
|
case xtpControlThemeFlat:
|
||
|
m_pTheme = new CXTPButtonFlatTheme();
|
||
|
break;
|
||
|
case xtpControlThemeUltraFlat:
|
||
|
m_pTheme = new CXTPButtonUltraFlatTheme();
|
||
|
break;
|
||
|
case xtpControlThemeOffice2000:
|
||
|
m_pTheme = new CXTPButtonOffice2000Theme();
|
||
|
break;
|
||
|
case xtpControlThemeOfficeXP:
|
||
|
m_pTheme = new CXTPButtonOfficeXPTheme();
|
||
|
break;
|
||
|
case xtpControlThemeOffice2003:
|
||
|
m_pTheme = new CXTPButtonOffice2003Theme();
|
||
|
break;
|
||
|
case xtpControlThemeResource:
|
||
|
m_pTheme = new CXTPButtonResourceTheme();
|
||
|
break;
|
||
|
default:
|
||
|
m_pTheme = new CXTPButtonTheme();
|
||
|
}
|
||
|
|
||
|
m_bUseVisualStyle = (eTheme == xtpControlThemeDefault);
|
||
|
|
||
|
RefreshMetrics();
|
||
|
|
||
|
return (m_pTheme != NULL);
|
||
|
}
|
||
|
|
||
|
void CXTPButton::SetUseVisualStyle(BOOL bUseVisualStyle/* = TRUE*/)
|
||
|
{
|
||
|
m_bUseVisualStyle = bUseVisualStyle;
|
||
|
m_pTheme->RefreshMetrics(this);
|
||
|
RedrawButton();
|
||
|
}
|
||
|
|
||
|
|
||
|
BOOL CXTPButton::GetChecked()
|
||
|
{
|
||
|
if (IsPushButton() || !m_hWnd)
|
||
|
{
|
||
|
return m_bChecked;
|
||
|
}
|
||
|
|
||
|
return (BOOL)::SendMessage(m_hWnd, BM_GETCHECK, 0, 0);
|
||
|
}
|
||
|
|
||
|
void CXTPButton::SetChecked(BOOL bChecked)
|
||
|
{
|
||
|
if (IsPushButton() || !m_hWnd)
|
||
|
{
|
||
|
m_bChecked = bChecked;
|
||
|
RedrawButton();
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
::SendMessage(m_hWnd, BM_SETCHECK, bChecked, 0);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
BOOL CXTPButton::SetIcon(CSize size, UINT nID, UINT nHotID/*= 0*/, BOOL bRedraw/*= TRUE*/)
|
||
|
{
|
||
|
return CXTPButton::SetIcon(
|
||
|
size, MAKEINTRESOURCE(nID), MAKEINTRESOURCE(nHotID), bRedraw);
|
||
|
}
|
||
|
|
||
|
BOOL CXTPButton::SetIcon(CSize size, LPCTSTR lpszID, LPCTSTR lpszHotID/*= NULL*/, BOOL bRedraw/*= TRUE*/)
|
||
|
{
|
||
|
CXTPImageManagerIconHandle hIcon;
|
||
|
CXTPImageManagerIconHandle hIconHot;
|
||
|
|
||
|
hIcon.CreateIconFromResource(lpszID, size);
|
||
|
|
||
|
// Return false if the icon handle is NULL.
|
||
|
if (hIcon.IsEmpty())
|
||
|
{
|
||
|
TRACE0("Failed to load Icon resource.\n");
|
||
|
return FALSE;
|
||
|
}
|
||
|
|
||
|
// If we are using a pushed image as well...
|
||
|
if (lpszHotID)
|
||
|
{
|
||
|
hIconHot.CreateIconFromResource(lpszHotID, size);
|
||
|
|
||
|
// Return false if the icon handle is NULL.
|
||
|
if (hIconHot.IsEmpty())
|
||
|
{
|
||
|
TRACE0("Failed to load Icon resource.\n");
|
||
|
return FALSE;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return CXTPButton::SetIcon(size, hIcon, hIconHot, bRedraw);
|
||
|
}
|
||
|
|
||
|
BOOL CXTPButton::SetIcon(CSize /*size*/, CXTPImageManagerIcon* pIcon, BOOL bRedraw/*= TRUE*/)
|
||
|
{
|
||
|
// Construct the icon manager.
|
||
|
CMDTARGET_RELEASE(m_pIcon);
|
||
|
|
||
|
m_pIcon = pIcon;
|
||
|
|
||
|
// Redraw the button.
|
||
|
if (bRedraw)
|
||
|
RedrawButton();
|
||
|
|
||
|
return TRUE;
|
||
|
}
|
||
|
|
||
|
BOOL CXTPButton::SetIcon(CSize size, const CXTPImageManagerIconHandle& hIcon, const CXTPImageManagerIconHandle& hIconHot, BOOL bRedraw/*= TRUE*/)
|
||
|
{
|
||
|
ASSERT(!hIcon.IsEmpty());
|
||
|
|
||
|
// Save the image size and set the icon
|
||
|
// handles to NULL.
|
||
|
size = size != CSize(0) ? size : hIcon.GetExtent();
|
||
|
|
||
|
CXTPImageManagerIcon* pIcon = new CXTPImageManagerIcon(0, size.cx, size.cy);
|
||
|
pIcon->SetIcon(hIcon);
|
||
|
|
||
|
if (!hIconHot.IsEmpty())
|
||
|
pIcon->SetHotIcon(hIconHot);
|
||
|
|
||
|
return SetIcon(size, pIcon, bRedraw);
|
||
|
}
|
||
|
|
||
|
|
||
|
BOOL CXTPButton::SetIcon(CSize size, HICON hIcon, HICON hIconHot/*= NULL*/, BOOL bRedraw/*= TRUE*/)
|
||
|
{
|
||
|
return SetIcon(size, CXTPImageManagerIconHandle(hIcon), CXTPImageManagerIconHandle(hIconHot), bRedraw);
|
||
|
}
|
||
|
|
||
|
BOOL CXTPButton::SetBitmap(CSize size, UINT nID, BOOL bRedraw/*= TRUE*/)
|
||
|
{
|
||
|
// Free previous resources (if any).
|
||
|
|
||
|
CXTPImageManagerIconHandle hIconHandle;
|
||
|
|
||
|
BOOL bAlphaBitmap = FALSE;
|
||
|
HBITMAP hBitmap = CXTPImageManagerIcon::LoadBitmapFromResource(MAKEINTRESOURCE(nID), &bAlphaBitmap);
|
||
|
|
||
|
if (!hBitmap)
|
||
|
return FALSE;
|
||
|
|
||
|
if (bAlphaBitmap)
|
||
|
{
|
||
|
hIconHandle = hBitmap; // Will call DeleteObject;
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
CBitmap bmpIcon;
|
||
|
bmpIcon.Attach(hBitmap);
|
||
|
|
||
|
// convert the bitmap to a transparent icon.
|
||
|
HICON hIcon = CXTPTransparentBitmap(bmpIcon).ConvertToIcon();
|
||
|
|
||
|
hIconHandle = hIcon; // Will call DestoyIcon;
|
||
|
}
|
||
|
|
||
|
if (hIconHandle.IsEmpty())
|
||
|
return FALSE;
|
||
|
|
||
|
return CXTPButton::SetIcon(size, hIconHandle, CXTPImageManagerIconHandle(), bRedraw);
|
||
|
}
|
||
|
|
||
|
void CXTPButton::SetBuddy(CWnd* pWndBuddy, BOOL bMoveButton)
|
||
|
{
|
||
|
m_hWndBuddy = pWndBuddy->GetSafeHwnd();
|
||
|
if (!m_hWndBuddy)
|
||
|
return;
|
||
|
|
||
|
CRect rcBuddy;
|
||
|
::GetWindowRect(m_hWndBuddy, &rcBuddy);
|
||
|
|
||
|
GetParent()->ScreenToClient(rcBuddy);
|
||
|
|
||
|
CXTPWindowRect rc(this);
|
||
|
int nWidth = rc.Width();
|
||
|
|
||
|
if (bMoveButton)
|
||
|
{
|
||
|
::MoveWindow(m_hWndBuddy, rcBuddy.left, rcBuddy.top, rcBuddy.Width() - nWidth + 2, rcBuddy.Height(), TRUE);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
GetParent()->ScreenToClient(rc);
|
||
|
::MoveWindow(m_hWndBuddy, rcBuddy.left, rcBuddy.top, (rc.left + 2) - rcBuddy.left, rcBuddy.Height(), TRUE);
|
||
|
rcBuddy.right = rc.left + nWidth;
|
||
|
}
|
||
|
|
||
|
CRect rcButton = rcBuddy;
|
||
|
rcButton.left = rcButton.right - nWidth;
|
||
|
|
||
|
::MoveWindow(m_hWnd, rcButton.left, rcButton.top, rcButton.Width(), rcButton.Height(), TRUE);
|
||
|
|
||
|
}
|
||
|
|
||
|
|
||
|
INT_PTR CXTPButton::OnToolHitTest(CPoint point, TOOLINFO* pTI) const
|
||
|
{
|
||
|
|
||
|
ASSERT_VALID(this);
|
||
|
ASSERT(::IsWindow(m_hWnd));
|
||
|
|
||
|
CString strTip = GetTooltip();
|
||
|
if (strTip.GetLength() == 0)
|
||
|
return -1;
|
||
|
|
||
|
CXTPButton* pButton = (CXTPButton*)this;
|
||
|
|
||
|
CXTPClientRect rc(pButton);
|
||
|
rc.DeflateRect(2, 2);
|
||
|
|
||
|
if (rc.PtInRect(point))
|
||
|
{
|
||
|
CXTPToolTipContext::FillInToolInfo(pTI, m_hWnd, rc, 1, strTip, pButton->GetButtonText(), strTip);
|
||
|
return 1;
|
||
|
}
|
||
|
|
||
|
return -1;
|
||
|
}
|