// XTPEdit.cpp : implementation of the CXTPEdit 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/XTPColorManager.h"
#include "Common/XTPResourceImage.h"
#include "Common/XTPMaskEditT.h"
#include "../Util/XTPControlTheme.h"
#include "Common/XTPWinThemeWrapper.h"

#include "../Edit/XTPEdit.h"
#include "XTPSpinButtonCtrl.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif


#define UD_HITNOWHERE 0
#define UD_HITDOWN 1
#define UD_HITUP 2


IMPLEMENT_DYNAMIC(CXTPSpinButtonCtrl, CSpinButtonCtrl)

/////////////////////////////////////////////////////////////////////////////
// CXTPMaskEdit
/////////////////////////////////////////////////////////////////////////////

CXTPSpinButtonCtrl::CXTPSpinButtonCtrl()
{
	m_bUseVisualStyle = TRUE;
	m_nTheme = xtpControlThemeDefault;

	m_nHotButton = UD_HITNOWHERE;
	m_nPressedButton = UD_HITNOWHERE;

	m_bPreSubclassInit = TRUE;

	m_themeSpin = new CXTPWinThemeWrapper();
}

CXTPSpinButtonCtrl::~CXTPSpinButtonCtrl()
{
	SAFE_DELETE(m_themeSpin);
}

BEGIN_MESSAGE_MAP(CXTPSpinButtonCtrl, CSpinButtonCtrl)
//{{AFX_MSG_MAP(CXTPSpinButtonCtrl)
	ON_WM_PAINT()
	ON_WM_ERASEBKGND()
	ON_WM_SIZE()
	ON_WM_SYSCOLORCHANGE()
	ON_WM_LBUTTONDOWN()
	ON_WM_LBUTTONUP()
	ON_WM_MOUSEMOVE()
	ON_MESSAGE_VOID(WM_MOUSELEAVE, OnMouseLeave)
	ON_WM_CREATE()
//}}AFX_MSG_MAP
END_MESSAGE_MAP()

void CXTPSpinButtonCtrl::Init()
{
	RefreshMetrics();

	Invalidate(FALSE);
}


void CXTPSpinButtonCtrl::PreSubclassWindow()
{
	CSpinButtonCtrl::PreSubclassWindow();

	if (m_bPreSubclassInit)
	{
		// Initialize the control.
		Init();
	}
}

int CXTPSpinButtonCtrl::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
	if (CSpinButtonCtrl::OnCreate(lpCreateStruct) == -1)
		return -1;

	// Initialize the control.
	Init();

	return 0;
}

BOOL CXTPSpinButtonCtrl::PreCreateWindow(CREATESTRUCT& cs)
{
	if (!CSpinButtonCtrl::PreCreateWindow(cs))
		return FALSE;

	// When creating controls dynamically Init() must
	// be called from OnCreate() and not from
	// PreSubclassWindow().

	m_bPreSubclassInit = FALSE;

	return TRUE;
}

void CXTPSpinButtonCtrl::OnPaint()
{
	CPaintDC dc(this); // device context for painting

	CXTPBufferDC dcMem(dc);
	OnDraw(&dcMem);
}

CXTPEdit* CXTPSpinButtonCtrl::GetEditBuddy() const
{
	HWND hWndBuddy = (HWND)::SendMessage(m_hWnd, UDM_GETBUDDY, 0, 0);
	if (!hWndBuddy)
		return FALSE;

	CXTPEdit* pEdit = DYNAMIC_DOWNCAST(CXTPEdit, CWnd::FromHandle(hWndBuddy));
	return pEdit;
}

BOOL CXTPSpinButtonCtrl::HasSharedBorder() const
{
	CXTPEdit* pEdit = GetEditBuddy();
	if (!pEdit)
		return FALSE;

	CXTPWindowRect rcEdit(pEdit);
	CXTPWindowRect rcSpin(this);

	CRect rcIntersect;
	if (!rcIntersect.IntersectRect(rcEdit, rcSpin))
		return FALSE;

	return rcIntersect.Width() == 2;

}

void CXTPSpinButtonCtrl::OnDraw(CDC* pDC)
{
	CRect rc;
	GetClientRect(&rc);

	pDC->FillSolidRect(rc, GetXtremeColor(COLOR_3DFACE));

	if (HasSharedBorder())
	{
		CXTPEdit* pEditBuddy = GetEditBuddy();
		pEditBuddy->DrawBuddyBorders(this, pDC, rc, GetStyle() & UDS_ALIGNRIGHT ? UDS_ALIGNRIGHT : UDS_ALIGNLEFT);
	}

	if (m_bUseVisualStyle && m_themeSpin->IsAppThemed())
	{
		DrawVisualStyle(pDC);
	}
	else if (m_nTheme == xtpControlThemeResource)
	{
		DrawOffice2007(pDC);
	}
	else if (m_nTheme != xtpControlThemeDefault)
	{
		DrawFlat(pDC);
	}
	else
	{
		DrawStandard(pDC);
	}
}

BOOL CXTPSpinButtonCtrl::IsVertical() const
{
	return (GetStyle() & UDS_HORZ) == 0;
}

void CXTPSpinButtonCtrl::DrawStandard(CDC* pDC)
{
	BOOL bEnabled = IsWindowEnabled();

	if (IsVertical())
	{
		UINT uFlags = DFCS_SCROLLUP;
		if (m_nPressedButton == UD_HITUP)
			uFlags |= DFCS_PUSHED;
		if (!bEnabled)
			uFlags |= DFCS_INACTIVE;

		CRect rc = GetButtonRect(UD_HITUP);
		DrawFrameControl(pDC->GetSafeHdc(), &rc, DFC_SCROLL, uFlags);

		uFlags = DFCS_SCROLLDOWN;
		if (m_nPressedButton == UD_HITDOWN)
			uFlags |= DFCS_PUSHED;
		if (!bEnabled)
			uFlags |= DFCS_INACTIVE;

		rc = GetButtonRect(UD_HITDOWN);
		DrawFrameControl(pDC->GetSafeHdc(), &rc, DFC_SCROLL, uFlags);
	}
	else
	{
		UINT uFlags = DFCS_SCROLLLEFT;
		if (m_nPressedButton == UD_HITDOWN)
			uFlags |= DFCS_PUSHED;
		if (!bEnabled)
			uFlags |= DFCS_INACTIVE;

		CRect rc = GetButtonRect(UD_HITDOWN);
		DrawFrameControl(pDC->GetSafeHdc(), &rc, DFC_SCROLL, uFlags);

		uFlags = DFCS_SCROLLRIGHT;
		if (m_nPressedButton == UD_HITUP)
			uFlags |= DFCS_PUSHED;
		if (!bEnabled)
			uFlags |= DFCS_INACTIVE;

		rc = GetButtonRect(UD_HITUP);
		DrawFrameControl(pDC->GetSafeHdc(), &rc, DFC_SCROLL, uFlags);
	}
}

void CXTPSpinButtonCtrl::DrawArrowGlyph2(CDC* pDC, CRect rcArrow, BOOL bHorz, BOOL bUpArrow, BOOL bEnabled)
{
	int nHeight = min(rcArrow.Width(), rcArrow.Height());
	if (nHeight < 6) return;

	int x = rcArrow.left + ((rcArrow.Width() - nHeight) / 2) + 2;
	int y = rcArrow.top + ((rcArrow.Height() - nHeight) / 2) + 2;
	nHeight -= 4;

	COLORREF clr = bEnabled ? RGB(0, 0, 0) : GetSysColor(COLOR_3DSHADOW);

	HFONT hFont = CreateFont(nHeight, 0, 0, 0, FW_NORMAL, 0, 0, 0, SYMBOL_CHARSET, 0, 0, 0, 0, _T("MARLETT"));
	HFONT hOldFont = (HFONT)SelectObject(pDC->GetSafeHdc(), hFont);

	SetTextColor(pDC->GetSafeHdc(), clr);
	pDC->SetBkMode(TRANSPARENT);
	TextOut(pDC->GetSafeHdc(), x, y, bHorz ? (!bUpArrow ? _T("3") : _T("4")) : (bUpArrow ? _T("5") : _T("6")), 1);

	SelectObject(pDC->GetSafeHdc(), hOldFont);
	DeleteObject(hFont);
}

void CXTPSpinButtonCtrl::DrawFlatButton(CDC* pDC, UINT nButton)
{
	BOOL bEnabled = IsWindowEnabled();
	CRect rc = GetButtonRect(nButton);

	pDC->FillSolidRect(rc, m_nPressedButton == nButton ? m_crBackPushed : m_nHotButton == nButton ? m_crBackHilite : m_crBack);

	if (m_nTheme != xtpControlThemeOffice2000)
	{
		COLORREF clr = m_nPressedButton == nButton || m_nHotButton == nButton ? m_crBorderHilite : m_crBorder;
		pDC->Draw3dRect(rc, clr, clr);
	}
	else
	{
		if (m_nPressedButton == nButton)
			pDC->Draw3dRect(rc, GetXtremeColor(COLOR_3DSHADOW), GetXtremeColor(COLOR_3DHIGHLIGHT));
		else
			pDC->Draw3dRect(rc, GetXtremeColor(COLOR_3DHIGHLIGHT), GetXtremeColor(COLOR_3DSHADOW));
	}

	if (m_nPressedButton == nButton && (m_nTheme == xtpControlThemeOffice2000 || m_nTheme == xtpControlThemeFlat))
		rc.OffsetRect(1, 1);

	DrawArrowGlyph2(pDC, rc, !IsVertical(), nButton == UD_HITUP, bEnabled);
}

void CXTPSpinButtonCtrl::DrawFlat(CDC* pDC)
{
	if (m_nHotButton == UD_HITUP)
	{
		DrawFlatButton(pDC, UD_HITDOWN);
		DrawFlatButton(pDC, UD_HITUP);
	}
	else
	{
		DrawFlatButton(pDC, UD_HITUP);
		DrawFlatButton(pDC, UD_HITDOWN);
	}
}

CRect GetCenterRect(CRect rc, CSize sz, int xOffset = 0, int yOffset = 0)
{
	return CRect( CPoint((rc.left + rc.right - sz.cx) / 2 + xOffset, (rc.top + rc.bottom - sz.cy) / 2 + yOffset), sz);
}


void CXTPSpinButtonCtrl::DrawOffice2007(CDC* pDC)
{
	BOOL bEnabled = IsWindowEnabled();


	CXTPResourceImages* pImages = XTPResourceImages();

	if (IsVertical())
	{
		CXTPResourceImage* pImage = pImages->LoadFile(_T("TOOLBARBUTTONSPINARROWSVERTICAL"));
		if (!pImage)
			return;

		CRect rcTop = GetButtonRect(UD_HITUP);
		CRect rcBottom = GetButtonRect(UD_HITDOWN);

		if (rcTop.bottom + 1 == rcBottom.top)
		{
			CRect rcBackSrc(pImage->GetSource(1, 10));
			rcBackSrc.top = rcBackSrc.bottom - 1;
			pImage->DrawImage(pDC, CRect(rcTop.left, rcTop.bottom, rcTop.right, rcBottom.top), rcBackSrc, CRect(2, 0, 2, 0), 0xFF00FF);
		}

		// Background
		{
			int nState = !bEnabled ? 4 : m_nPressedButton == UD_HITUP ? 3 : m_nHotButton == UD_HITUP ? 2 :  1;
			pImage->DrawImage(pDC, rcTop, pImage->GetSource(nState, 10), CRect(2, 2, 2, 2), 0xFF00FF);

			nState = !bEnabled ? 9 : m_nPressedButton == UD_HITDOWN ? 8 : m_nHotButton == UD_HITDOWN ? 7 : 6;
			pImage->DrawImage(pDC, rcBottom, pImage->GetSource(nState, 10), CRect(2, 2, 2, 2), 0xFF00FF);
		}

		// Glyphs
		{
			pImage = rcTop.Width() > 12 && rcTop.Height() > 12 ?
				pImages->LoadFile(_T("CONTROLGALLERYSCROLLARROWGLYPHS")) :
			pImages->LoadFile(_T("TOOLBARBUTTONSPINARROWGLYPHS"));

			if (!pImage)
				return;

			int nState = !bEnabled ? 3 : m_nPressedButton == UD_HITUP ? 2 : m_nHotButton == UD_HITUP ? 1 :  0;
			CRect rcSrc = pImage->GetSource(nState, 16);
			pImage->DrawImage(pDC, GetCenterRect(rcTop, rcSrc.Size()), rcSrc, CRect(0, 0, 0, 0), 0xFF00FF);

			nState = 4 + (!bEnabled ? 3 : m_nPressedButton == UD_HITUP ? 2 : m_nHotButton == UD_HITUP ? 1 :  0);
			rcSrc = pImage->GetSource(nState, 16);
			pImage->DrawImage(pDC, GetCenterRect(rcBottom, rcSrc.Size()), rcSrc, CRect(0, 0, 0, 0), 0xFF00FF);
		}
	}
	else
	{
		CXTPResourceImage* pImage = pImages->LoadFile(_T("TOOLBARBUTTONSPINARROWSHORIZONTAL"));
		if (!pImage)
			return;

		CRect rcTop = GetButtonRect(UD_HITUP);
		CRect rcBottom = GetButtonRect(UD_HITDOWN);

		if (rcBottom.right + 1 == rcTop.left)
		{
			CRect rcBackSrc(pImage->GetSource(1, 10));
			rcBackSrc.left = rcBackSrc.right - 1;
			pImage->DrawImage(pDC, CRect(rcBottom.right, rcTop.top, rcTop.left, rcTop.bottom), rcBackSrc, CRect(0, 2, 0, 2), 0xFF00FF);
		}

		// Background
		{
			int nState = 5 + (!bEnabled ? 4 : m_nPressedButton == UD_HITUP ? 3 : m_nHotButton == UD_HITUP ? 2 :  1);
			pImage->DrawImage(pDC, rcTop, pImage->GetSource(nState, 10), CRect(2, 2, 2, 2), 0xFF00FF);

			nState = !bEnabled ? 4 : m_nPressedButton == UD_HITDOWN ? 3 : m_nHotButton == UD_HITDOWN ? 2 : 1;
			pImage->DrawImage(pDC, rcBottom, pImage->GetSource(nState, 10), CRect(2, 2, 2, 2), 0xFF00FF);
		}

		// Glyphs
		{
			pImage = rcTop.Width() > 12 && rcTop.Height() > 12 ?
				pImages->LoadFile(_T("CONTROLGALLERYSCROLLARROWGLYPHS")) :
			pImages->LoadFile(_T("TOOLBARBUTTONSPINARROWGLYPHS"));

			if (!pImage)
				return;

			int nState = 12 + (!bEnabled ? 3 : m_nPressedButton == UD_HITUP ? 2 : m_nHotButton == UD_HITUP ? 1 :  0);
			CRect rcSrc = pImage->GetSource(nState, 16);
			pImage->DrawImage(pDC, GetCenterRect(rcTop, rcSrc.Size()), rcSrc, CRect(0, 0, 0, 0), 0xFF00FF);

			nState = 8 + (!bEnabled ? 3 : m_nPressedButton == UD_HITUP ? 2 : m_nHotButton == UD_HITUP ? 1 :  0);
			rcSrc = pImage->GetSource(nState, 16);
			pImage->DrawImage(pDC, GetCenterRect(rcBottom, rcSrc.Size()), rcSrc, CRect(0, 0, 0, 0), 0xFF00FF);
		}
	}
}

CRect CXTPSpinButtonCtrl::GetButtonRect(int nButton)
{
	CRect rc;
	GetClientRect(&rc);

	if (HasSharedBorder())
	{
		CXTPEdit* pEditBuddy = GetEditBuddy();
		pEditBuddy->AdjustBuddyRect(this, rc, GetStyle() & UDS_ALIGNRIGHT ? UDS_ALIGNRIGHT : UDS_ALIGNLEFT);
	}

	BOOL bOverride = (m_nTheme == xtpControlThemeUltraFlat || m_nTheme == xtpControlThemeOfficeXP || m_nTheme == xtpControlThemeOffice2003 ||
		m_nTheme == xtpControlThemeFlat);

	if (bOverride && m_bUseVisualStyle && m_themeSpin->IsAppThemed())
		bOverride = FALSE;

	if (!IsVertical())
	{
		int nWidth = (rc.Width() + (bOverride ? 1 : 0)) / 2;
		if (nButton == UD_HITDOWN)
			rc.right = rc.left + nWidth;
		else
			rc.left = bOverride ? rc.left + nWidth - 1 : rc.right - nWidth;
	}
	else
	{
		int nHeight = (rc.Height() + (bOverride ? 1 : 0)) / 2;
		if (nButton == UD_HITUP)
			rc.bottom = rc.top + nHeight;
		else
			rc.top = bOverride ? rc.top + nHeight - 1 : rc.bottom - nHeight;
	}

	return rc;
}

void CXTPSpinButtonCtrl::DrawVisualStyle(CDC* pDC)
{
	BOOL bEnabled = IsWindowEnabled();

	if (!IsVertical())
	{
		int nState = DNHZS_NORMAL;
		if (!bEnabled)
			nState = DNHZS_DISABLED;
		else if (m_nPressedButton == UD_HITDOWN && m_nHotButton == UD_HITDOWN)
			nState = DNHZS_PRESSED;
		else if ((m_nHotButton == UD_HITDOWN || m_nPressedButton == UD_HITDOWN)  && (m_nPressedButton != UD_HITUP))
			nState = DNHZS_HOT;

		CRect rc = GetButtonRect(UD_HITDOWN);
		m_themeSpin->DrawThemeBackground(pDC->GetSafeHdc(), SPNP_DOWNHORZ, nState, &rc, NULL);


		nState = UPHZS_NORMAL;
		if (!bEnabled)
			nState = UPHZS_DISABLED;
		else if (m_nPressedButton == UD_HITUP && m_nHotButton == UD_HITUP)
			nState = UPHZS_PRESSED;
		else if ((m_nHotButton == UD_HITUP || m_nPressedButton == UD_HITUP) && (m_nPressedButton != UD_HITDOWN))
			nState = UPHZS_HOT;

		rc = GetButtonRect(UD_HITUP);
		m_themeSpin->DrawThemeBackground(pDC->GetSafeHdc(), SPNP_UPHORZ, nState, &rc, NULL);

	}
	else
	{
		int nState = UPS_NORMAL;
		if (!bEnabled)
			nState = UPS_DISABLED;
		else if (m_nPressedButton == UD_HITUP && m_nHotButton == UD_HITUP)
			nState = UPS_PRESSED;
		else if ((m_nHotButton == UD_HITUP || m_nPressedButton == UD_HITUP) && (m_nPressedButton != UD_HITDOWN))
			nState = UPS_HOT;

		CRect rc = GetButtonRect(UD_HITUP);
		m_themeSpin->DrawThemeBackground(pDC->GetSafeHdc(), SPNP_UP, nState, &rc, NULL);

		nState = DNS_NORMAL;
		if (!bEnabled)
			nState = DNS_DISABLED;
		else if (m_nPressedButton == UD_HITDOWN && m_nHotButton == UD_HITDOWN)
			nState = DNS_PRESSED;
		else if ((m_nHotButton == UD_HITDOWN || m_nPressedButton == UD_HITDOWN)  && (m_nPressedButton != UD_HITUP))
			nState = DNS_HOT;

		rc = GetButtonRect(UD_HITDOWN);
		m_themeSpin->DrawThemeBackground(pDC->GetSafeHdc(), SPNP_DOWN, nState, &rc, NULL);
	}

}



BOOL CXTPSpinButtonCtrl::OnEraseBkgnd(CDC* /*pDC*/)
{
	return TRUE;
}

void CXTPSpinButtonCtrl::OnSize(UINT nType, int cx, int cy)
{
	CSpinButtonCtrl::OnSize(nType, cx, cy);

	Invalidate(FALSE);
}

void CXTPSpinButtonCtrl::RefreshMetrics()
{
	XTPColorManager()->RefreshColors();

	m_themeSpin->CloseTheme();

	if (m_bUseVisualStyle)
	{
		m_themeSpin->OpenTheme(0, L"SPIN");
	}

	COLORREF clrWindow = GetXtremeColor(COLOR_WINDOW);
	COLORREF clrFace = GetXtremeColor(COLOR_3DFACE);

	m_crBackHilite = m_crBackPushed = m_crBack = clrFace;
	m_crBorderHilite = GetXtremeColor(COLOR_3DSHADOW);
	m_crBorder = GetXtremeColor(COLOR_3DSHADOW);

	if (m_nTheme == xtpControlThemeUltraFlat)
	{

		COLORREF clrPushed = GetXtremeColor(COLOR_3DSHADOW);
		clrPushed = XTPColorManager()->LightColor(clrPushed, clrFace, 0x32);
		m_crBackPushed = clrPushed;

		COLORREF clrHighlight = clrFace;
		clrHighlight = XTPColorManager()->LightColor(clrHighlight, clrWindow, 0x1E);
		m_crBackHilite = clrHighlight;
	}
	else if ((m_nTheme == xtpControlThemeOfficeXP) || (m_nTheme == xtpControlThemeOffice2003))
	{
		m_crBackPushed = GetXtremeColor(XPCOLOR_HIGHLIGHT_PUSHED);
		m_crBackHilite = GetXtremeColor(XPCOLOR_HIGHLIGHT);
		m_crBorderHilite = GetXtremeColor(XPCOLOR_HIGHLIGHT_BORDER);


		XTPCurrentSystemTheme systemTheme = m_nTheme == xtpControlThemeOffice2003 ? XTPColorManager()->GetCurrentSystemTheme() : xtpSystemThemeUnknown;
		switch (systemTheme)
		{
		case xtpSystemThemeBlue:
		case xtpSystemThemeRoyale:
		case xtpSystemThemeAero:
			m_crBorder = RGB(127, 157, 185);
			m_crBackHilite = RGB(0, 0, 128);
			m_crBack = RGB(169, 199, 240);
			break;

		case xtpSystemThemeOlive:
			m_crBorder = RGB(164, 185, 127);
			m_crBackHilite = RGB(63, 93, 56);
			m_crBack = RGB(197, 212, 159);
			break;

		case xtpSystemThemeSilver:
			m_crBorder = RGB(165, 172, 178);
			m_crBackHilite = RGB(75, 75, 11);
			m_crBack = RGB(192, 192, 211);
			break;
		}

		if (systemTheme != xtpSystemThemeUnknown)
		{
			m_crBackHilite = RGB(255, 238, 194);
			m_crBackPushed = RGB(254, 128, 62);
		}
	}
	else if (m_nTheme == xtpControlThemeFlat)
	{
		m_crBorder = m_crBorderHilite = GetXtremeColor(COLOR_WINDOWFRAME);
	}

}

UINT CXTPSpinButtonCtrl::HitTest(CPoint pt)
{
	CRect rc;
	GetClientRect(&rc);

	if (!rc.PtInRect(pt))
		return UD_HITNOWHERE;

	if (GetStyle() & UDS_HORZ)
	{
		// Horizontal placement
		if (pt.x < (rc.right / 2))
		{
			return UD_HITDOWN;
		}
		else if (pt.x > (rc.right / 2))
		{
			return UD_HITUP;
		}
	}
	else
	{
		if (pt.y > (rc.bottom / 2))
		{
			return UD_HITDOWN;
		}
		else if (pt.y < (rc.bottom / 2))
		{
			return UD_HITUP;
		}
	}

	return UD_HITNOWHERE;
}



void CXTPSpinButtonCtrl::OnMouseMove(UINT nFlags, CPoint point)
{
	UINT uHot = HitTest(point);

	if (uHot != m_nHotButton)
	{
		m_nHotButton = uHot;
		Invalidate(FALSE);

		if (m_nHotButton != UD_HITNOWHERE)
		{
			TRACKMOUSEEVENT tme = {sizeof(TRACKMOUSEEVENT), TME_LEAVE, m_hWnd, HOVER_DEFAULT};
			_TrackMouseEvent(&tme);
		}
	}

	CSpinButtonCtrl::OnMouseMove(nFlags, point);
}

void CXTPSpinButtonCtrl::OnMouseLeave()
{
	OnMouseMove(0, CPoint(-1, -1));
}

void CXTPSpinButtonCtrl::OnLButtonDown(UINT nFlags, CPoint point)
{
	CSpinButtonCtrl::OnLButtonDown(nFlags, point);

	UINT uHot = HitTest(point);

	if (uHot != HTNOWHERE)
	{
		m_nPressedButton = uHot;
		Invalidate(FALSE);
	}

}

void CXTPSpinButtonCtrl::OnLButtonUp(UINT nFlags, CPoint point)
{
	if (m_nPressedButton != HTNOWHERE)
	{
		m_nPressedButton = HTNOWHERE;
		Invalidate(FALSE);
	}

	CSpinButtonCtrl::OnLButtonUp(nFlags, point);
}


void CXTPSpinButtonCtrl::SetUseVisualStyle(BOOL bUseVisualStyle/* = TRUE*/)
{
	m_bUseVisualStyle = bUseVisualStyle;

	RefreshMetrics();

	if (m_hWnd) Invalidate(FALSE);
}

void CXTPSpinButtonCtrl::SetTheme(XTPControlTheme nTheme)
{
	m_nTheme = nTheme;

	m_bUseVisualStyle = (m_nTheme == xtpControlThemeDefault);

	RefreshMetrics();

	if (m_hWnd) Invalidate(FALSE);
}