 |
|
 |
void CSeparator::OnPaint()
{
CPaintDC dc(this); CRect rectWnd; CRect rectText; CString cstrText; CFont* pfontOld;
DWORD dwStyle = GetStyle();
GetWindowRect ( rectWnd );
GetClientRect ( rectText );
GetWindowText ( cstrText );
if ( rectWnd.Height() > rectWnd.Width() )
{
dc.Draw3dRect(
rectWnd.Width()/2, 0, 2, rectWnd.Height(), ::GetSysColor(COLOR_3DSHADOW),
::GetSysColor(COLOR_3DHIGHLIGHT) );
}
else
{
pfontOld = dc.SelectObject ( GetFont() );
SIZE TextSize;
GetTextExtentPoint32(dc, cstrText, cstrText.GetLength(), &TextSize);
UINT uFormat = DT_TOP;
if ( dwStyle & SS_NOPREFIX )
uFormat |= DT_NOPREFIX;
static const int nLineTop = (rectWnd.Height() / 2) + 2; static const int nSmallLineWidth = 5; static const int nLineThickness = 2; static const int nTextLineDistance = 3;
if ( dwStyle & SS_RIGHT )
{
uFormat |= DT_RIGHT;
dc.Draw3dRect (0,
nLineTop,
rectWnd.Width() - TextSize.cx - 2*nTextLineDistance - nSmallLineWidth,
nLineThickness,
::GetSysColor(COLOR_3DSHADOW),
::GetSysColor(COLOR_3DHIGHLIGHT) );
dc.Draw3dRect (rectWnd.Width() - nSmallLineWidth,
nLineTop,
nSmallLineWidth,
nLineThickness,
::GetSysColor(COLOR_3DSHADOW),
::GetSysColor(COLOR_3DHIGHLIGHT) );
}
else if ( dwStyle & SS_CENTER )
{
uFormat |= DT_CENTER;
dc.Draw3dRect (0, nLineTop,
((rectWnd.Width() - TextSize.cx) / 2) - nTextLineDistance,
nLineThickness,
::GetSysColor(COLOR_3DSHADOW),
::GetSysColor(COLOR_3DHIGHLIGHT) );
dc.Draw3dRect (((rectWnd.Width() + TextSize.cx) / 2) + nTextLineDistance,
nLineTop,
((rectWnd.Width() - TextSize.cx) / 2) - nTextLineDistance,
nLineThickness,
::GetSysColor(COLOR_3DSHADOW),
::GetSysColor(COLOR_3DHIGHLIGHT) );
}
else
{
uFormat |= DT_LEFT;
dc.Draw3dRect(0, nLineTop, nSmallLineWidth, nLineThickness,
::GetSysColor(COLOR_3DSHADOW),
::GetSysColor(COLOR_3DHIGHLIGHT) );
int nLeft = nSmallLineWidth + TextSize.cx + 2*nTextLineDistance;
dc.Draw3dRect (nLeft,
nLineTop,
rectWnd.Width() - nLeft,
nLineThickness,
::GetSysColor(COLOR_3DSHADOW),
::GetSysColor(COLOR_3DHIGHLIGHT) );
}
dc.SetBkMode(TRANSPARENT);
if ( (dwStyle & SS_RIGHT) == SS_RIGHT)
rectText.OffsetRect( - (nSmallLineWidth + nTextLineDistance), 0);
else if ((dwStyle & SS_LEFT) == SS_LEFT)
rectText.OffsetRect((nSmallLineWidth + nTextLineDistance), 0);
if (!IsWindowEnabled())
{
dc.SetTextColor( ::GetSysColor(COLOR_3DHIGHLIGHT));
CRect rect = rectText;
rect.OffsetRect(1,1);
dc.DrawText( cstrText, &rect, uFormat);
dc.SetTextColor( ::GetSysColor(COLOR_3DSHADOW));
dc.SetBkMode(TRANSPARENT);
}
dc.DrawText ( cstrText, rectText, uFormat );
dc.SelectObject ( pfontOld );
}
}
Michael !
|
|
|
|
 |
|
 |
Use a picture control,reduce the height/width to a line, change the color to etched ..i think thats good enough rather than this class.
modified on Thursday, April 10, 2008 5:59 AM
|
|
|
|
 |
|
 |
void CSeparator::OnPaint() { CPaintDC dc(this); // device context for painting CRect rectWnd; // RECT of the static control CRect rectText; // RECT in which text will be drawn CString cstrText; // text to draw CFont* pfontOld; DWORD dwStyle = GetStyle(); // this window's style // Get the screen & client coords. GetWindowRect ( rectWnd ); GetClientRect ( rectText ); // Get the text to be drawn. GetWindowText ( cstrText ); // If the control is taller than it is wide, draw a vertical line. // No text is drawn in this case. if ( rectWnd.Height() > rectWnd.Width() ) { dc.Draw3dRect( rectWnd.Width()/2, 0, // upper-left point 2, rectWnd.Height(), // width & height ::GetSysColor(COLOR_3DSHADOW), ::GetSysColor(COLOR_3DHIGHLIGHT) ); /************************************************************ If you feel adventurous, here is the code to do vertical text drawing. I have it commented out because getting the text aligned correctly over the line looks like it'll be a pain. // Start by getting this control's font, and then tweak it a bit. LOGFONT lf; GetFont()->GetObject ( sizeof(LOGFONT), &lf ); // Text will be rotated counter-clockwise 90 degrees. lf.lfOrientation = lf.lfEscapement = 900; // We need a TrueType font to get rotated text. MS Sans Serif // won't cut it! lstrcpy ( lf.lfFaceName, _T("Tahoma") ); // Create a font with the tweaked attributes. CFont font; font.CreateFontIndirect ( &lf ); pfontOld = dc.SelectObject ( &font ); dc.SetBkColor ( ::GetSysColor(COLOR_BTNFACE) ); GetWindowText ( cstrText ); dc.DrawText ( cstrText, rectText, DT_VCENTER | DT_CENTER | DT_SINGLELINE ); dc.SelectObject ( pfontOld ); font.DeleteObject(); ************************************************************/ } else { // Get the font for the text. pfontOld = dc.SelectObject ( GetFont() ); SIZE TextSize; GetTextExtentPoint32(dc, cstrText, cstrText.GetLength(), &TextSize); // We're drawing a horizontal separator. // The text will always be at the top of the control. Also check // if the SS_NOPREFIX style is set. // Voila! One 3D line coming up. UINT uFormat = DT_TOP; if ( dwStyle & SS_NOPREFIX ) uFormat |= DT_NOPREFIX; if ( dwStyle & SS_RIGHT ) { uFormat |= DT_RIGHT; dc.Draw3dRect (0, rectWnd.Height() / 2, rectWnd.Width() - TextSize.cx - 10, 2, ::GetSysColor(COLOR_3DSHADOW), ::GetSysColor(COLOR_3DHIGHLIGHT) ); } else if ( dwStyle & SS_CENTER ) { uFormat |= DT_CENTER; dc.Draw3dRect (0, rectWnd.Height() / 2, ((rectWnd.Width() - TextSize.cx) / 2) - 10, 2, ::GetSysColor(COLOR_3DSHADOW), ::GetSysColor(COLOR_3DHIGHLIGHT) ); dc.Draw3dRect (((rectWnd.Width() - TextSize.cx) / 2) + TextSize.cx + 10, rectWnd.Height() / 2, ((rectWnd.Width() - TextSize.cx) / 2) - 10, 2, ::GetSysColor(COLOR_3DSHADOW), ::GetSysColor(COLOR_3DHIGHLIGHT) ); } else { uFormat |= DT_LEFT; dc.Draw3dRect (TextSize.cx + 10, rectWnd.Height() / 2, rectWnd.Width() - TextSize.cx - 10, 2, ::GetSysColor(COLOR_3DSHADOW), ::GetSysColor(COLOR_3DHIGHLIGHT) ); } dc.SetBkMode(TRANSPARENT); dc.DrawText ( cstrText, rectText, uFormat ); // Clean up GDI objects like a good lil' programmer. dc.SelectObject ( pfontOld ); } }
|
|
|
|
 |
|
 |
Hi katsyonak!
Thanks for posting these fixes! The class now works perfectly for my purposes.
And thanks to Michael Dunn for this neat class!
Regards, mYkel
|
|
|
|
 |
|
 |
If you want to have a separator line with disabled text.. like at the bottom of the InstallShield wizard... then replace the code at the bottom of OnPaint() with this code:
dc.SetBkColor ( ::GetSysColor(COLOR_BTNFACE) );
if (!IsWindowEnabled())
{
dc.SetTextColor( ::GetSysColor(COLOR_3DHIGHLIGHT));
CRect rect = rectText;
rect.OffsetRect(1,1);
dc.DrawText( cstrText, &rect, uFormat);
dc.SetTextColor( ::GetSysColor(COLOR_3DSHADOW));
dc.SetBkMode(TRANSPARENT);
}
dc.DrawText ( cstrText, rectText, uFormat );
|
|
|
|
 |
|
 |
With a XP themed application the background of the text shows the control color instead of the shaded themed background. I looked into this code and tried adding SetBKMode(TRANSPARENT), this works but the line shows through the text, I also tried adding the offset of the string size but I assume this gets initialized after the drawing. The string length + 2 from the text needs to be sent as the x offset to start drawing the line after the text. I would dive deeper into this if I had more time but I don't. It would be great if someone hacked this together.
|
|
|
|
 |
|