It is mainly implemented through the ownerdraw attribute.
1. Run Appwizard to generate a test project based on the dialog box, and add a cbutton control to the dialog box. On the general properties page of The cbutton control, change the control ID to idc_3dtextbtn, set caption to "who is crazy", select ownerdraw on the styles property page of the control, and keep the remaining settings by default.
2. Use classwizard to create a new class: c3dtextbutton. The base class is cbutton.
3. Add a protected function void draw (CDC * PDC, const crect & rect, uint State) to the c3dtextbutton class ). Write the Code as follows:
Void c3dtextbutton: Draw (CDC * PDC, const crect & rect, uint state)
{
Cstring text;
Getwindowtext (text );
Int L = text. getlength ();
Crect rectclient = rect;
// Obtain the control font
Cfont * pfont = getfont ();
// Determine the valid font height and width
Logfont;
Pfont-> GetObject (sizeof (logfont), & logfont );
If (logfont. lfheight = 0) logfont. lfheight = 20;
Logfont. lfwidth = 0;
// Set the width to 0, and the width value is determined by the height.
Logfont. lfWeight = 1000;
Logfont. lfEscapement = logfont. lfOrientation = 0;
CFont tryfont;
VERIFY (tryfont. CreateFontIndirect (& logfont ));
CFont * pFontOld = pDC-> SelectObject (& tryfont );
// Adjust the font height based on the widget size to coordinate the text with the widget
CSize textSizeClient = pDC-> GetTextExtent (text, l );
If (rectClient. Width () * textSizeClient. cy> rectClient. Height () * textSizeClient. cx)
{
Logfont. lfHeight =: MulDiv (logfont. lfHeight, rectClient. Height (), textSizeClient. cy );
}
Else
{
Logfont. lfHeight =: MulDiv (logfont. lfHeight, rectClient. Width (), textSizeClient. cx );
}
// Create and select the coordinated font
CFont font;
Font. CreateFontIndirect (& logfont );
PDC-> SelectObject (& font );
TextSizeClient = pDC-> GetTextExtent (text, l );
// Determine the distance between the text and the control boundary minx and miny
Int minx = rectClient. left + (rectClient. Width ()-textSizeClient. cx)/2;
Int miny = rectClient. top + (rectClient. Height ()-textSizeClient. cy)/2;
Int oldBkMode = pDC-> SetBkMode (TRANSPARENT );
COLORREF textcol =: GetSysColor (COLOR_BTNTEXT );
COLORREF oldTextColor = pDC-> SetTextColor (textcol );
Int cx = minx;
Int cy = miny;
Int s = (state & ODS_SELECTED )? -1: + 1;
Cx + = 3;
Cy + = 3;
// 3D effect
PDC-> SetTextColor (: GetSysColor (COLOR_3DDKSHADOW ));
PDC-> TextOut (cx-s * 2, cy + s * 2, text );
PDC-> textout (cx + S * 2, cy-S * 2, text );
PDC-> textout (cx + S * 2, Cy + S * 2, text );
PDC-> settextcolor (: getsyscolor (color_3dhilight ));
PDC-> textout (cx + S * 1, cy-S * 2, text );
PDC-> textout (CX-S * 2, Cy + S * 1, text );
PDC-> textout (CX-S * 2, cy-S * 2, text );
PDC-> settextcolor (: getsyscolor (color_3dshadow ));
PDC-> textout (CX-S * 1, Cy + S * 1, text );
PDC-> textout (cx + S * 1, cy-S * 1, text );
PDC-> textout (cx + S * 1, Cy + S * 1, text );
PDC-> settextcolor (: getsyscolor (color_3dlight ));
PDC-> textout (CX, cy-S * 1, text );
PDC-> textout (CX-S * 1, Cy, text );
PDC-> textout (CX-S * 1, cy-S * 1, text );
PDC-> settextcolor (textcol );
// Output the title
PDC-> textout (CX, Cy, text );
// Restore the device description table
PDC-> SetTextColor (oldTextColor );
PDC-> SetBkMode (oldBkMode );
PDC-> SelectObject (pFontOld );}
4. Use classwizard to reload the DrawItem function of the C3dTextButton class. Write the Code as follows:
Void C3dTextButton: DrawItem (LPDRAWITEMSTRUCT lpDrawItemStruct)
{
// TODO: Add your code to draw the specified item
CDC * pDC = CDC: FromHandle (lpDrawItemStruct-> hDC );
ASSERT_VALID (pDC );
CRect rectClient = lpDrawItemStruct-> rcItem;
Draw (pDC, rectClient, lpDrawItemStruct-> itemState );
}
5. Use classwizard to create a C3dTextButton control variable m_3dTextButton1 for IDC_3DTEXTBTN.
6. Add "3dTextButton. h" to the header file testDlg.
7. Compile and test the application. Look ~