Click here to Skip to main content
15,885,767 members
Articles / Desktop Programming / MFC

Irregular shaped buttons – owner drawn buttons made easy

Rate me:
Please Sign up or sign in to vote.
4.93/5 (44 votes)
21 Sep 2005CPOL4 min read 116.2K   3.8K   81  
Freehand draw - make a button with irregular shape. A step by step beginner's guide.
// MyButton.cpp : implementation file
//

#include "stdafx.h"
#include "ButtonSub.h"
#include "MyButton.h"
#include <time.h>


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

/////////////////////////////////////////////////////////////////////////////
// CMyButton

CMyButton::CMyButton()
{
}

CMyButton::~CMyButton()
{
}


BEGIN_MESSAGE_MAP(CMyButton, CButton)
	//{{AFX_MSG_MAP(CMyButton)
	//}}AFX_MSG_MAP
END_MESSAGE_MAP()

/////////////////////////////////////////////////////////////////////////////
// CMyButton message handlers




void CMyButton::PreSubclassWindow() 
{
	ModifyStyle(0,BS_OWNERDRAW);
	CButton::PreSubclassWindow();
}

#ifdef _SAMPLE1

void CMyButton::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct) 
{
	SetWindowRgn(rgn,TRUE);			// Construct your buttons region. This wont reflect in your view. But you can sense it by clicking the region area.

	CDC* pDC=CDC::FromHandle(lpDrawItemStruct->hDC);	// Get dc for the button
	
	switch(lpDrawItemStruct->itemAction) 
	{
		case ODA_SELECT:
		{
			GetParent()->Invalidate();
		}							// no break; for this case
		case ODA_DRAWENTIRE:
		{
			if(lpDrawItemStruct->itemState & ODS_SELECTED)	
			{
				pDC->FillRgn(CRgn::FromHandle(trgn), CBrush::FromHandle((HBRUSH)GetStockObject(GRAY_BRUSH)));
			}
			// Draw button down state
			else
			{
				pDC->FillRgn(CRgn::FromHandle(trgn), CBrush::FromHandle((HBRUSH)GetStockObject(BLACK_BRUSH)));
				HRGN r= ::CreateRectRgn(0,0,0,0);
				CombineRgn(r,trgn,0,RGN_COPY);
				OffsetRgn(r,2,2);
				pDC->FillRgn(CRgn::FromHandle(r), CBrush::FromHandle((HBRUSH)GetStockObject(GRAY_BRUSH)));
			}
			break;
		}
		case ODA_FOCUS: 
		{
				pDC->FillRgn(CRgn::FromHandle(trgn),CBrush::FromHandle((HBRUSH)GetStockObject(LTGRAY_BRUSH))); 
		}
		break;
	}
	// Draw button caption.
}

#endif



void CMyButton::SetRgn(CRgn *region)
{
	rgn=::CreateRectRgn(0,0,0,0); 
	CombineRgn(rgn,region->operator HRGN(),NULL,RGN_COPY);
	trgn=::CreateRectRgn(0,0,0,0);
	CombineRgn(trgn,region->operator HRGN(),NULL,RGN_COPY);
}

#ifdef _SAMPLE2

void CMyButton::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct) 
{
   UINT uStyle = DFCS_BUTTONPUSH;

   // This code only works with buttons.
   ASSERT(lpDrawItemStruct->CtlType == ODT_BUTTON);

   // If drawing selected, add the pushed style to DrawFrameControl.
   if (lpDrawItemStruct->itemState & ODS_SELECTED)
      uStyle |= DFCS_PUSHED;

   // Draw the button frame.
   ::DrawFrameControl(lpDrawItemStruct->hDC, &lpDrawItemStruct->rcItem, 
      DFC_BUTTON, uStyle);

   // Get the button's text.
   CString strText;
   GetWindowText(strText);

   // Draw the button text using the text color red.
   COLORREF crOldColor = ::SetTextColor(lpDrawItemStruct->hDC, RGB(255,0,0));
   ::DrawText(lpDrawItemStruct->hDC, strText, strText.GetLength(), 
      &lpDrawItemStruct->rcItem, DT_SINGLELINE|DT_VCENTER|DT_CENTER);
   ::SetTextColor(lpDrawItemStruct->hDC, crOldColor);
}

#endif

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer
India India
Naren started coding during 1999 with FORTRAN, then COBOL, PASCAL, C, C++, VC++ ..... C#, Java, ASP so on, till today. He claims himself as techie who loves coding, but he is not even sure which technology or platform he loves, most of the time Windows, some time WinCE, some time Linux, nowadays Android and embedded platforms. He can do some query stuffs with Oracle, SQL Server, MySQL. He strongly believes that C/C++ is a must for all programmers, "if you know C/C++, you can do programming on any language". He is an electronic gadget guy who likes to buy small gadgets all the time, at least he will do window shopping on a gadget shop. His interest always have been with Automation in any form, call it a little automated program sitting in his Laptop or a home automation program runs on his mobile. Apart from coding, he likes to do...???

Comments and Discussions