【MFC】控件自绘之CSliderCtrl

一:

     我们通过继承MFC自带的CSliderCtrl,并且重写一个OnPaint函数。当然其实也可以通过继承CStatic去模拟CSliderCtrl来实现自绘。自绘难度并不大。国际惯例,上代码。

 

二:

h 头文件

class CSkinSliderCtrl : public CSliderCtrl
{
	DECLARE_DYNAMIC(CSkinSliderCtrl)

public:
	CSkinSliderCtrl();
	virtual ~CSkinSliderCtrl();

	void SetImage(CString strBkImage, CString strThumb);

protected:
	DECLARE_MESSAGE_MAP()

	afx_msg BOOL     OnEraseBkgnd(CDC* pDC);
	afx_msg void     OnPaint();
	afx_msg LRESULT  OnMouseLeave(WPARAM wparam, LPARAM lparam);
	afx_msg void     OnMouseMove(UINT nFlags, CPoint point);

private:
	void DrawChannel(CDC *pDC, LPNMCUSTOMDRAW lpcd);
	void DrawThumb(CDC *pDC, LPNMCUSTOMDRAW lpcd);
	CRect GetStateRect(int nThumb);

private:
	BOOL                m_bTracking;
	BOOL                m_bThumb;

	CImage              m_imBg;
	CImage              m_imThumb;
};


cpp源文件

IMPLEMENT_DYNAMIC(CSkinSliderCtrl, CSliderCtrl)
CSkinSliderCtrl::CSkinSliderCtrl()
{
	m_bTracking   = FALSE;
	m_bThumb      = FALSE;
}

CSkinSliderCtrl::~CSkinSliderCtrl()
{
}


BEGIN_MESSAGE_MAP(CSkinSliderCtrl, CSliderCtrl)
	ON_WM_ERASEBKGND()
	ON_WM_PAINT()
	ON_WM_MOUSEMOVE()
	ON_MESSAGE(WM_MOUSELEAVE, OnMouseLeave)
END_MESSAGE_MAP()


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

void CSkinSliderCtrl::OnPaint()
{
	CPaintDC     dc(this);
	CRect        rect;
	GetClientRect(rect);
	CMemDCC      DCMemory(&dc, &rect);
	
	DCMemory.SetStretchBltMode(COLORONCOLOR);
	DCMemory.FillSolidRect(&rect, GetSysColor(CTLCOLOR_DLG));

	//此处要视图片而定到底怎么画
	CRect rcChannel;
	GetChannelRect(rcChannel);
	m_imBg.StretchBlt(DCMemory.m_hDC, rcChannel);

	int iState = 0;
	if (m_bThumb)
	{
		iState = 2;
	}

	CRect rectThumb;
	GetThumbRect(&rectThumb);

	m_imThumb.TransparentBlt(DCMemory.m_hDC, rectThumb, GetStateRect(iState), RGB(255, 0, 0));
}

void CSkinSliderCtrl::OnMouseMove(UINT nFlags, CPoint point)
{
	if (!m_bTracking)
	{
		TRACKMOUSEEVENT tme;
		tme.cbSize = sizeof(tme);
		tme.hwndTrack = m_hWnd;
		tme.dwFlags = TME_LEAVE|TME_HOVER;
		tme.dwHoverTime = 1;
		m_bTracking = _TrackMouseEvent(&tme);		
	}

	CRect rectThumb;
	GetThumbRect(&rectThumb);
	rectThumb.PtInRect(point)?m_bThumb = TRUE : m_bThumb = FALSE;

	CSliderCtrl::OnMouseMove(nFlags, point);
}

LRESULT CSkinSliderCtrl::OnMouseLeave(WPARAM wparam, LPARAM lparam)
{
	m_bTracking = FALSE;
	m_bThumb    = FALSE;

	Invalidate();

	return S_OK;
}

CRect CSkinSliderCtrl::GetStateRect(int nThumb)
{
	if(m_imThumb.IsNull())
		return CRect(0, 0, 0, 0);

	int nX = m_imThumb.GetWidth()/4;
	int nY = m_imThumb.GetHeight();

	return CRect(nX*nThumb, 0, (nThumb+1)*nX, nY);
}

void CSkinSliderCtrl::SetImage(CString strBkImage, CString strThumb)
{
	m_imBg.Load(strBkImage);
	m_imThumb.Load(strThumb);

	ASSERT(!m_imBg.IsNull());
	ASSERT(!m_imThumb.IsNull());
}


 

 

你可能感兴趣的:(【MFC】控件自绘之CSliderCtrl)