Exemplo n.º 1
0
void CEnEdit::DrawEnabledText(CDC* pDC, const CPoint& ptTopLeft, const CString& sText, 
						const CRect& rect, BOOL bEnabled, BOOL bSymbol)
{
	if (bEnabled)
	{
		pDC->SetTextColor(GetSysColor(COLOR_BTNTEXT));
		DrawText(pDC, ptTopLeft, sText, rect, bSymbol);
	}
	else // disabled
	{
		// draw embossed: dark over pale
		CPoint ptText(ptTopLeft);

		ptText.Offset(1, 1);
		pDC->SetTextColor(GetSysColor(COLOR_3DHIGHLIGHT));
		DrawText(pDC, ptText, sText, rect, bSymbol);
		
		ptText.Offset(-1, -1);
		pDC->SetTextColor(GetSysColor(COLOR_3DSHADOW));
		DrawText(pDC, ptText, sText, rect, bSymbol);
	}
}
CXTPChartDeviceCommand* CXTPChartRadarAxisXView::CreateConstantLinesDeviceCommand(CXTPChartDeviceContext* pDC, BOOL bBehind)
{
	CXTPChartAxisConstantLines* pConstantLines = m_pAxis->GetConstantLines();
	if (pConstantLines->GetCount() == 0)
		return NULL;

	CXTPChartDeviceCommand* pCommands = new CXTPChartDeviceCommand();

	for (int i = 0; i < pConstantLines->GetCount(); i++)
	{
		CXTPChartAxisConstantLine* pConstantLine = pConstantLines->GetAt(i);
		if (!pConstantLine->IsVisible())
			continue;

		if (pConstantLine->IsShowBehind() != bBehind)
			continue;

		double dMark = !pConstantLine->GetAxisValue().IsEmpty() ? m_pAxis->GetScaleTypeMap()->ValueToInternal(pConstantLine->GetAxisValue()) :
			pConstantLine->GetAxisValueInternal();

		double lineAngle = ValueToAngle(dMark);

		CXTPPoint3d ptEnd(m_ptCenter.X + cos(lineAngle) * m_nRadius, m_ptCenter.Y - sin(lineAngle) * m_nRadius);

		pCommands->AddChildCommand(pConstantLine->GetLineStyle()->CreateDeviceCommand(CXTPPoint3d(m_ptCenter),
			ptEnd, pConstantLine->GetActualColor()));

		CXTPChartString strText = pConstantLine->GetText();

		CPoint ptText(int(m_ptCenter.X + cos(lineAngle) * (m_nRadius - 5)), int(m_ptCenter.Y - sin(lineAngle) * (m_nRadius - 5)));

		CXTPChartRotatedTextPainterNearLine painter(pDC, strText, pConstantLine, ptText, xtpChartTextNearTop, -(float)CXTPChartMathUtils::Radian2Degree(lineAngle));
			pCommands->AddChildCommand(painter.CreateDeviceCommand(pDC, pConstantLine->GetActualTextColor()));

	}

	return pCommands;
}
Exemplo n.º 3
0
int TextCuller::insertLinebreaks(TokenString& tstring, int max_line_length, int breaks_per_line)
{
	assert(max_line_length > 0);
	assert(breaks_per_line >= 1);

	unsigned int token = 0;
	int line_len = 0;

	auto& tokens = tstring.tokens;

	while (token < tokens.size()) {
		if (tokens[token].type == PrintTokenType::TEXT) {
			line_len += tokens[token].text.length();

			if (line_len > max_line_length) {
				string text = tokens[token].text;

				//Split
				int dif = line_len - max_line_length;
				int len = text.length();
				string _before = text.substr(0, len - dif);
				string _after = text.substr(len - dif);

				//Possibly try to split on word boundary (space)
				size_t look = _before.find_last_of(' ');

				if (look != string::npos && //no ' ' before split
					look != 0)              //re-splitting at the first character is dumb
				{
					string _new_before = _before.substr(0, look);
					string _after_prefix = _before.substr(look+1);

					_before = _new_before;
					_after = _after_prefix + _after;
				}

				//Prepare tokens
				TokenString replace;

				for (int i = 0; i < breaks_per_line; ++i)
					replace.push_back(ptNewline());

				replace.tokens.insert(replace.begin(), ptText(_before));
				replace.tokens.push_back(ptText(_after));

				//Replace
				tokens.erase(tokens.begin() + token);
				tokens.insert(tokens.begin() + token, replace.begin(), replace.end());

				//We finish pointing to the newline we made.
				token += 1;
			}
		}

		//OH MY F*****G GOD WHY ISN'T THIS A WARNING. I HAD = INSTEAD OF ==. F**K!!!!
		if (tokens[token].type == PrintTokenType::NEWLINE) {
			line_len = 0;
		}

		++token;
	}

	return tstring.num_lines();
}
Exemplo n.º 4
0
void CToolTipCtrlX::OnNMCustomDraw(NMHDR *pNMHDR, LRESULT *pResult)
{
	LPNMTTCUSTOMDRAW pNMCD = reinterpret_cast<LPNMTTCUSTOMDRAW>(pNMHDR);
	if (pNMCD->nmcd.dwDrawStage == CDDS_PREPAINT)
	{
		CWnd* pwnd = CWnd::FromHandle(pNMCD->nmcd.hdr.hwndFrom);
		CDC* pdc = CDC::FromHandle(pNMCD->nmcd.hdc);

		CString strText;
		pwnd->GetWindowText(strText);

		CRect rcWnd;
		pwnd->GetWindowRect(&rcWnd);
		CRect rcBorder;
		rcBorder.left = pNMCD->nmcd.rc.left - rcWnd.left;
		rcBorder.top = pNMCD->nmcd.rc.top - rcWnd.top;
		rcBorder.right = rcWnd.right - pNMCD->nmcd.rc.right;
		rcBorder.bottom = rcWnd.bottom - pNMCD->nmcd.rc.bottom;

		if (m_bCol1Bold && m_fontBold.m_hObject == NULL) 
		{
			CFont* pFont = pwnd->GetFont();
			if (pFont) {
				LOGFONT lf;
				pFont->GetLogFont(&lf);
				lf.lfWeight = FW_BOLD;
				VERIFY( m_fontBold.CreateFontIndirect(&lf) );
			}
		}

		int iTextHeight = 0;
		int iMaxCol1Width = 0;
		int iMaxCol2Width = 0;
		int iMaxSingleLineWidth = 0;
		CSize sizText(0);
		int iPos = 0;
		while (iPos != -1)
		{
			CString strLine = GetNextString(strText, _T('\n'), iPos);
			int iColon = strLine.Find(_T(':'));
			if (iColon != -1) {
				CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
				CSize siz = pdc->GetTextExtent(strLine, iColon + 1);
				if (pOldFont)
					pdc->SelectObject(pOldFont);
				iMaxCol1Width = max(iMaxCol1Width, siz.cx);
				iTextHeight = siz.cy; // update height with 'col1' string, because 'col2' string might be empty and therefore has no height
				sizText.cy += siz.cy;

				LPCTSTR pszCol2 = (LPCTSTR)strLine + iColon + 1;
				while (_istspace(*pszCol2))
					pszCol2++;
				if (*pszCol2 != _T('\0')) {
					siz = pdc->GetTextExtent(pszCol2, ((LPCTSTR)strLine + strLine.GetLength()) - pszCol2);
					iMaxCol2Width = max(iMaxCol2Width, siz.cx);
				}
			}
			else if (!strLine.IsEmpty()) {
				CSize siz = pdc->GetTextExtent(strLine);
				iMaxSingleLineWidth = max(iMaxSingleLineWidth, siz.cx);
				sizText.cy += siz.cy;
			}
			else {
				CSize siz = pdc->GetTextExtent(_T(" "), 1);
				sizText.cy += siz.cy;
			}
		}
		iMaxCol1Width = min(m_iScreenWidth4, iMaxCol1Width);
		iMaxCol2Width = min(m_iScreenWidth4*2, iMaxCol2Width);

		const int iMiddleMargin = 6;
		iMaxSingleLineWidth = max(iMaxSingleLineWidth, iMaxCol1Width + iMiddleMargin + iMaxCol2Width);
		sizText.cx = iMaxSingleLineWidth;

		rcWnd.right = rcWnd.left + rcBorder.left + sizText.cx + rcBorder.right;
		rcWnd.bottom = rcWnd.top + rcBorder.top + sizText.cy + rcBorder.bottom;

		if (rcWnd.left >= m_rcScreen.left) {
			if (rcWnd.right > m_rcScreen.right && rcWnd.Width() <= m_rcScreen.Width())
				rcWnd.OffsetRect(-(rcWnd.right - m_rcScreen.right), 0);
		}
		if (rcWnd.top >= m_rcScreen.top) {
			if (rcWnd.bottom > m_rcScreen.bottom && rcWnd.Height() <= m_rcScreen.Height())
				rcWnd.OffsetRect(0, -(rcWnd.bottom - m_rcScreen.bottom));
		}

		pwnd->MoveWindow(&rcWnd);

		pwnd->ScreenToClient(&rcWnd);
		pdc->FillSolidRect(&rcWnd, m_crTooltipBkColor);

		CPoint ptText(pNMCD->nmcd.rc.left, pNMCD->nmcd.rc.top);
		iPos = 0;
		while (iPos != -1)
		{
			CString strLine = GetNextString(strText, _T('\n'), iPos);
			int iColon = strLine.Find(_T(':'));
			if (iColon != -1) {
				CRect rcDT(ptText.x, ptText.y, ptText.x + iMaxCol1Width, ptText.y + iTextHeight);
				// don't draw empty <col1> strings (they are still handy to use for skipping the <col1> space)
				if (iColon > 0) {
					CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
					pdc->DrawText(strLine, iColon + 1, &rcDT, m_dwCol1DrawTextFlags);
					if (pOldFont)
						pdc->SelectObject(pOldFont);
				}

				LPCTSTR pszCol2 = (LPCTSTR)strLine + iColon + 1;
				while (_istspace(*pszCol2))
					pszCol2++;
				if (*pszCol2 != _T('\0')) {
					rcDT.left = ptText.x + iMaxCol1Width + iMiddleMargin;
					rcDT.right = rcDT.left + iMaxCol2Width;
					pdc->DrawText(pszCol2, ((LPCTSTR)strLine + strLine.GetLength()) - pszCol2, &rcDT, m_dwCol2DrawTextFlags);
				}

				ptText.y += iTextHeight;
			}
			else {
				CSize siz = pdc->TabbedTextOut(ptText.x, ptText.y, strLine, 0, NULL, 0);
				ptText.y += siz.cy;
			}
		}

		*pResult = CDRF_SKIPDEFAULT;
		return;
	}

	*pResult = CDRF_DODEFAULT;
}
Exemplo n.º 5
0
void CToolTipCtrlX::OnNMCustomDraw(NMHDR *pNMHDR, LRESULT *pResult)
{
	LPNMTTCUSTOMDRAW pNMCD = reinterpret_cast<LPNMTTCUSTOMDRAW>(pNMHDR);
	if (pNMCD->nmcd.dwDrawStage == CDDS_PREPAINT)
	{
		CWnd* pwnd = CWnd::FromHandle(pNMCD->nmcd.hdr.hwndFrom);
		CDC* pdc = CDC::FromHandle(pNMCD->nmcd.hdc);

		CString strText;
		pwnd->GetWindowText(strText);

		CRect rcWnd;
		pwnd->GetWindowRect(&rcWnd);

		CFont* pOldDCFont = NULL;
		if (m_fontNormal.m_hObject != NULL){
			 pOldDCFont = pdc->SelectObject(&m_fontNormal);
		}
		if (m_bCol1Bold && m_fontBold.m_hObject == NULL) {
			CFont* pFont = pwnd->GetFont();
			if (pFont) {
				LOGFONT lf;
				pFont->GetLogFont(&lf);
				lf.lfWeight = FW_BOLD;
				VERIFY( m_fontBold.CreateFontIndirect(&lf) );
			}
		}
		pdc->SetTextColor(m_crTooltipTextColor);


		int iTextHeight = 0;
		int iMaxCol1Width = 0;
		int iMaxCol2Width = 0;
		int iMaxSingleLineWidth = 0;
		CSize sizText(0);
		int iPos = 0;
		int iCaptionEnd = m_bShowFileIcon ? max(strText.Find(_T("\n<br_head>\n")), 0) : 0; // special tooltip with file icon
		int iCaptionHeigth = 0;
		int iIconMinYBorder = 3;
		int iIconSize = theApp.GetBigSytemIconSize().cx;
		int iIconDrawingSpace = iIconSize + 9;
		while (iPos != -1)
		{
			CString strLine = GetNextString(strText, _T('\n'), iPos);
			int iColon = strLine.Find(_T(':'));
			if (iColon != -1) {
				CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
				CSize siz = pdc->GetTextExtent(strLine, iColon + 1);
				if (pOldFont)
					pdc->SelectObject(pOldFont);
				iMaxCol1Width = max(iMaxCol1Width, siz.cx + ((m_bShowFileIcon && iPos <= iCaptionEnd + strLine.GetLength()) ? iIconDrawingSpace : 0));
				iTextHeight = siz.cy + 1; // update height with 'col1' string, because 'col2' string might be empty and therefore has no height
				if (iPos <= iCaptionEnd)
					iCaptionHeigth += siz.cy + 1;
				else
					sizText.cy += siz.cy + 1;

				LPCTSTR pszCol2 = (LPCTSTR)strLine + iColon + 1;
				while (_istspace((_TUCHAR)*pszCol2))
					pszCol2++;
				if (*pszCol2 != _T('\0')) {
					siz = pdc->GetTextExtent(pszCol2, ((LPCTSTR)strLine + strLine.GetLength()) - pszCol2);
					iMaxCol2Width = max(iMaxCol2Width, siz.cx);
				}
			}
			else if (m_bShowFileIcon && iPos <= iCaptionEnd && iPos == strLine.GetLength() + 1){
				// file name, printed bold on top without any tabbing or desc
				CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
				CSize siz = pdc->GetTextExtent(strLine);
				if (pOldFont)
					pdc->SelectObject(pOldFont);
				iMaxSingleLineWidth = max(iMaxSingleLineWidth, siz.cx + iIconDrawingSpace);
				iCaptionHeigth += siz.cy + 1;

			}
			else if (!strLine.IsEmpty() && strLine.Compare(_T("<br>")) != 0 && strLine.Compare(_T("<br_head>")) != 0) {
				CSize siz = pdc->GetTextExtent(strLine);
				iMaxSingleLineWidth = max(iMaxSingleLineWidth, siz.cx + ((iPos <= iCaptionEnd) ? iIconDrawingSpace : 0));
				if (m_bShowFileIcon && iPos <= iCaptionEnd + strLine.GetLength())
					iCaptionHeigth += siz.cy + 1;
				else
					sizText.cy += siz.cy + 1;
			}
			else{
				CSize siz = pdc->GetTextExtent(_T(" "), 1);
				sizText.cy += siz.cy;
			}
		}
		if (m_bShowFileIcon && iCaptionEnd > 0)
			iCaptionHeigth = max(iCaptionHeigth, iIconSize + (2*iIconMinYBorder));
		sizText.cy += iCaptionHeigth;

		iMaxCol1Width = min(m_iScreenWidth4, iMaxCol1Width);
		iMaxCol2Width = min(m_iScreenWidth4*2, iMaxCol2Width);

		const int iMiddleMargin = 6;
		iMaxSingleLineWidth = max(iMaxSingleLineWidth, iMaxCol1Width + iMiddleMargin + iMaxCol2Width);
		sizText.cx = iMaxSingleLineWidth;
	
		CRect rcNewSize(rcWnd.left, rcWnd.top, rcWnd.left + sizText.cx, rcWnd.top + sizText.cy);
		AdjustRect(&rcNewSize);		
		rcWnd.right = rcWnd.left + rcNewSize.Width();
		rcWnd.bottom = rcWnd.top + rcNewSize.Height();



		if (rcWnd.left >= m_rcScreen.left) {
			if (rcWnd.right > m_rcScreen.right && rcWnd.Width() <= m_rcScreen.Width())
				rcWnd.OffsetRect(-(rcWnd.right - m_rcScreen.right), 0);
		}
		if (rcWnd.top >= m_rcScreen.top) {
			if (rcWnd.bottom > m_rcScreen.bottom && rcWnd.Height() <= m_rcScreen.Height())
				rcWnd.OffsetRect(0, -(rcWnd.bottom - m_rcScreen.bottom));
		}
		CPoint ptText(pNMCD->nmcd.rc.left, pNMCD->nmcd.rc.top);

		pwnd->MoveWindow(&rcWnd);
		pwnd->ScreenToClient(&rcWnd);
		pNMCD->nmcd.rc.right = rcWnd.right; 
		pNMCD->nmcd.rc.bottom = rcWnd.bottom;
		pdc->FillSolidRect(&rcWnd, m_crTooltipBkColor);

		
		iPos = 0;
		while (iPos != -1)
		{
			CString strLine = GetNextString(strText, _T('\n'), iPos);
			int iColon = strLine.Find(_T(':'));
			CRect rcDT;
			if (!m_bShowFileIcon || (unsigned)iPos > (unsigned)iCaptionEnd + strLine.GetLength())
				rcDT.SetRect(ptText.x, ptText.y, ptText.x + iMaxCol1Width, ptText.y + iTextHeight);
			else
				rcDT.SetRect(ptText.x + iIconDrawingSpace, ptText.y, ptText.x + iMaxCol1Width, ptText.y + iTextHeight);
			if (iColon != -1) {
				// don't draw empty <col1> strings (they are still handy to use for skipping the <col1> space)
				if (iColon > 0) {
					CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
					pdc->DrawText(strLine, iColon + 1, &rcDT, m_dwCol1DrawTextFlags);
					if (pOldFont)
						pdc->SelectObject(pOldFont);
				}

				LPCTSTR pszCol2 = (LPCTSTR)strLine + iColon + 1;
				while (_istspace((_TUCHAR)*pszCol2))
					pszCol2++;
				if (*pszCol2 != _T('\0')) {
					rcDT.left = ptText.x + iMaxCol1Width + iMiddleMargin;
					rcDT.right = rcDT.left + iMaxCol2Width;
					pdc->DrawText(pszCol2, ((LPCTSTR)strLine + strLine.GetLength()) - pszCol2, &rcDT, m_dwCol2DrawTextFlags);
				}

				ptText.y += iTextHeight;
			}
			else if (m_bShowFileIcon && iPos <= iCaptionEnd && iPos == strLine.GetLength() + 1){
				// first line on special fileicon tab - draw icon and bold filename
				CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
				pdc->DrawText(strLine, CRect(ptText.x  + iIconDrawingSpace, ptText.y, ptText.x + iMaxSingleLineWidth, ptText.y + iTextHeight), m_dwCol1DrawTextFlags);
				if (pOldFont)
					pdc->SelectObject(pOldFont);

				ptText.y += iTextHeight;
				int iImage = theApp.GetFileTypeSystemImageIdx(strLine, -1, true);
				if (theApp.GetBigSystemImageList() != NULL)
					::ImageList_Draw(theApp.GetBigSystemImageList(), iImage, pdc->GetSafeHdc(), ptText.x, rcDT.top + ((iCaptionHeigth - iIconSize) / 2), ILD_NORMAL|ILD_TRANSPARENT);
			}
			else {
				if (strLine.Compare(_T("<br>")) == 0 || strLine.Compare(_T("<br_head>")) == 0){
					CPen pen;
					pen.CreatePen(0, 1, m_crTooltipTextColor);
					CPen *pOP = pdc->SelectObject(&pen);
					pdc->MoveTo(ptText.x, ptText.y + ((iTextHeight - 2) / 2)); 
					pdc->LineTo(ptText.x + iMaxSingleLineWidth, ptText.y + ((iTextHeight - 2) / 2));
					ptText.y += iTextHeight;
					pdc->SelectObject(pOP);
					pen.DeleteObject();
				}
				else{
					CSize siz = pdc->TabbedTextOut(ptText.x, ptText.y, strLine, 0, NULL, 0);
					ptText.y += siz.cy;
				}
			}
		}
		if (pOldDCFont)
			pdc->SelectObject(pOldDCFont);
		*pResult = CDRF_SKIPDEFAULT;
		return;
	}
	*pResult = CDRF_DODEFAULT;
}
Exemplo n.º 6
0
//@mFunc draws the listbox items in their proper state
void CQSLItemList::DrawItem( LPDRAWITEMSTRUCT lpDrawItemStruct )
{
	CDC* pDC = CDC::FromHandle(lpDrawItemStruct->hDC);

	QSLItemData itemData;
	GetItemData( lpDrawItemStruct->itemID, itemData );
	
#ifdef USECACHE
	RImage* pImage = GetCachedBitmap( lpDrawItemStruct->itemID ) ;
#else
	RImage* pImage = itemData.GetImage();

	if (!itemData.m_pImage)
	{
		itemData.m_pImage = pImage;
		SetItemData( lpDrawItemStruct->itemID, itemData );
	}

//	HBITMAP hBitmap = itemData.m_hBitmap ;
//	HPALETTE hPalette = itemData.m_hPalette ;
	
//	if (!itemData.m_pImage)
//	{
//		hBitmap = itemData.m_hBitmap = 
//			LoadBitmapPreview( lpDrawItemStruct->itemID, &itemData.m_hPalette ) ;
//		hPalette = itemData.m_hPalette;
//
//		// Save the new data into the control
//		SetItemData( lpDrawItemStruct->itemID, itemData );
//	}
//
//	// If we have a palette with the bitmap, realize it into the DC prior to painting.
//	if (hPalette != NULL)
//	{
//		CPalette palBitmap;
//		palBitmap.Attach( hPalette );
//		CPalette *pOldPal = pDC->SelectPalette( &palBitmap, TRUE );
//		pDC->RealizePalette();
//		pDC->SelectPalette( pOldPal, TRUE );
//		palBitmap.Detach();
//	}
#endif

	BITMAP  bm= { 0, 0, 0, 0, 0, 0, NULL };
	HBITMAP hBitmap = NULL;
	
	if (pImage)
	{
		hBitmap = (HBITMAP) pImage->GetSystemHandle();
		::GetObject( hBitmap, sizeof( bm ), &bm );
	}

	// Determine colors to use for drawing text and selection
	//
	COLORREF crFillColor = GetSysColor( COLOR_WINDOW ) ;
	COLORREF crTextColor = GetSysColor( COLOR_WINDOWTEXT ) ;

	if (lpDrawItemStruct->itemState & ODS_SELECTED)
	{
		crFillColor = GetSysColor( COLOR_HIGHLIGHT ) ;
		crTextColor = GetSysColor( COLOR_HIGHLIGHTTEXT ) ;
	}

	// Handle drawing according to action
	//

	// Setup DC
	COLORREF oldTextColor = pDC->SetTextColor( crTextColor );
	COLORREF oldBkColor   = pDC->SetBkColor( crFillColor );
	CFont* pOldFont = pDC->SelectObject( GetParent()->GetFont() );

	// Determine location to draw bitmap.  This information 
	// is needed for all drawing modes, so might as well
	// just determine it once, and in one place.
	CSize	  szExtent = pDC->GetTextExtent( itemData.m_strDesc );

	RIntRect  cellRect( lpDrawItemStruct->rcItem );
	cellRect.Inset( RIntSize( 4, 4 ) );
	cellRect.m_Bottom -= szExtent.cy + 2; // + 2 is for spacing between graphic & text

	RIntRect  imgRect( 0, 0, bm.bmWidth - 1, bm.bmHeight - 1 );
	imgRect.ShrinkToFit( cellRect );
	imgRect.CenterRectInRect( cellRect );

	CSize  szImage( imgRect.Width(), imgRect.Height() );
//	CPoint centerPt( cellRect.CenterPoint() );
//	CPoint ptTopLeft( centerPt.x - szImage.cx / 2, centerPt.y - szImage.cy / 2 - 2 );

	switch (lpDrawItemStruct->itemAction)
	{
	case ODA_DRAWENTIRE:
		{
		CDC memDC;
		memDC.CreateCompatibleDC( pDC );

		// Get the bitmap
		CBitmap* pBmp    = CBitmap::FromHandle( hBitmap );
		CBitmap* pOldBmp = memDC.SelectObject( pBmp );

		pDC->StretchBlt( imgRect.m_Left, imgRect.m_Top, imgRect.Width(), imgRect.Height(), 
			&memDC, 0, 0, bm.bmWidth, bm.bmHeight, SRCCOPY );

		memDC.SelectObject( pOldBmp );

		if (!(lpDrawItemStruct->itemState & ODS_SELECTED))
		{
			break ;
		}

		// Fall through
		}

	case ODA_SELECT:
		{
		// Draw/Clear the highlight rect
//		CRect bmpRect( ptTopLeft.x, ptTopLeft.y, ptTopLeft.x + bm.bmWidth, ptTopLeft.y + bm.bmHeight);
		
		CRect bmpRect( imgRect );
		bmpRect.InflateRect( 2, 2 );

		CPen pen( PS_SOLID, 2, crFillColor );
		CPen* pOldPen = pDC->SelectObject( &pen );

		pDC->MoveTo( bmpRect.left, bmpRect.top );
		pDC->LineTo( bmpRect.right, bmpRect.top );
		pDC->LineTo( bmpRect.right, bmpRect.bottom );
		pDC->LineTo( bmpRect.left, bmpRect.bottom );
		pDC->LineTo( bmpRect.left, bmpRect.top );
		pDC->SelectObject( pOldPen );
		}

	} // switch

	// Draw the text
	CPoint ptText( cellRect.m_Left + (cellRect.Width() - szExtent.cx) / 2, cellRect.m_Bottom + 4 );
	pDC->TextOut( ptText.x, ptText.y, itemData.m_strDesc );

//	pDC->DrawText( itemData.m_strDesc, &textRect, DT_CALCRECT | DT_SINGLELINE  );
//	textRect.OffsetRect( -textRect.Width() / 2, 2 );
//	pDC->DrawText( itemData.m_strDesc, &textRect, DT_CENTER | DT_VCENTER );

	// restore DC
	pDC->SelectObject( pOldFont );
	pDC->SetTextColor( oldTextColor );
	pDC->SetBkColor( oldBkColor );
}
Exemplo n.º 7
0
void WindowEdit::onRender( RenderContext & context, const RectInt & window )
{
	if (! windowStyle() )
		return;

	DisplayDevice * pDisplay = context.display();
	ASSERT( pDisplay );
	Font * pFont = windowStyle()->font();
	ASSERT( pFont );

	// calculate the total text size
	SizeInt textSize( pFont->size( WideString( m_Text ) ) );
	// get the text color
	Color textColor( windowStyle()->color() );
	textColor.m_A = m_Editing ? ACTIVE_ALPHA : INACTIVE_ALPHA;

	SizeInt windowSize( window.size() );

	// check the size of the window compared to the text size
	m_EditBegin = 0;
	m_EditEnd = m_Text.length() - 1;
	while ( textSize.m_Width > windowSize.m_Width )
	{
		if ( m_EditBegin < m_Cursor )
		{
			textSize.m_Width -= pFont->characterWidth( m_Text[ m_EditBegin ] );
			m_EditBegin++;
		}
		else if ( m_EditEnd > m_Cursor )
		{
			textSize.m_Width -= pFont->characterWidth( m_Text[ m_EditEnd ] );
			m_EditEnd--;
		}
		else	// not enough room, the font is probably too large so just return
			return;
	}

	// extract the displayable part of the text
	WideString display( m_Text );
	display.mid( m_EditBegin, (m_EditEnd - m_EditBegin) + 1 );

	// draw text left justified and centered vertically
	PointInt ptText( window.m_Left, window.m_Top + ((windowSize.m_Height / 2) - (textSize.m_Height / 2)) );
	// draw the text, construct another PointInt on the stack because Font::push will modify the point
	PointInt ptText2 = ptText;
	Font::push( pDisplay, pFont, ptText2, display, textColor );

	// display cursor if editing
	if ( m_Editing )
	{
		// draw cursor
		for(int i=m_EditBegin;i<m_Cursor;i++)
			ptText.m_X += pFont->characterWidth( m_Text[i] );

		Color cursorColor( textColor );
		cursorColor.m_A = (u8)(fmod( m_ActiveTime, CURSOR_BLINK_RATE ) * 255);

		RectInt cursorRect( ptText, SizeInt( CURSOR_WIDTH, textSize.height ) );

		PrimitiveMaterial::push( pDisplay, PrimitiveMaterial::ADDITIVE );
		PrimitiveWindow::push( pDisplay, cursorRect , RectFloat(0,0,0,0), cursorColor );
	}
}
Exemplo n.º 8
0
void CEnEdit::DrawButton(CDC* pDC, const CRect& rWindow, int nBtn, const CPoint& ptCursor) const
{
	const EDITBTN& eb = m_aButtons[nBtn];

	CRect rBtn = GetButtonRectByIndex(nBtn);

	if (rBtn.IsRectEmpty())
		return;

	int nSaveDC = pDC->SaveDC();

	BOOL bThemed = CThemed().AreControlsThemed();
	BOOL bHot = rBtn.PtInRect(ptCursor);
	BOOL bEnabled = (IsWindowEnabled() && eb.bEnabled);
	BOOL bDown = (m_nButtonDown == nBtn || eb.bChecked);

	rBtn.OffsetRect(-rWindow.TopLeft());

	// nasty business here because the API function DrawThemeEdge() is not theme aware!
	// and drawing a themed combostyle button will also draw the arrow which we don't want
	if (!m_bComboStyle || bThemed)	// draw as button type (for now)
	{
		UINT nFlags = DFCS_ADJUSTRECT | DFCS_BUTTONPUSH;
		
		// note: we do not take account of ES_READONLY as the effect of this
		// is not deterministic at this level so we assume derived classes or 
		// parents have handled it
		if (!bEnabled)
			nFlags |= DFCS_INACTIVE;
		
		else if (bDown)
			nFlags |= DFCS_PUSHED;
		
		else if (bHot)
			nFlags |= DFCS_HOT;
		
		// clip the drawing rect to prevent window getting the parent bkgnd color wrong
		CRect rClip(rBtn);

		if (bThemed)
			rBtn.InflateRect(1, 1);
		
		// for now
		CThemed::DrawFrameControl(this, pDC, rBtn, DFC_BUTTON, nFlags, rClip);
	}
	else // unthemed combo style
	{
		if (bEnabled && bDown)
			pDC->DrawEdge(rBtn, BDR_RAISEDOUTER, BF_RECT | BF_MIDDLE | BF_FLAT);
		else
		{
			pDC->DrawEdge(rBtn, BDR_RAISEDOUTER, BF_ADJUST | BF_RECT | BF_MIDDLE);
			pDC->DrawEdge(rBtn, BDR_RAISEDINNER, BF_RECT | BF_MIDDLE);
		}
	}

	// drop menu arrow
	if (eb.bDropMenu)
	{
		CRect rArrow(rBtn);
		
		if (bDown)
			rArrow.OffsetRect(1, 1);

		UINT nFlags = DT_END_ELLIPSIS | DT_VCENTER | DT_SINGLELINE | DT_NOPREFIX | DT_NOCLIP;

		if (eb.sCaption.IsEmpty())
			nFlags |= DT_CENTER;
		else
		{
			nFlags |= DT_RIGHT;
			rArrow.right -= 2;
		}

		pDC->SetTextColor(GetSysColor(bEnabled ? COLOR_BTNTEXT : COLOR_3DSHADOW));
		GraphicsMisc::DrawSymbol(pDC, MENU_DROPBTN, rArrow, nFlags, &GraphicsMisc::Marlett());
	}
	
	if (!eb.sCaption.IsEmpty())
	{
		// draw custom caption
		if (m_nButtonDown == nBtn || eb.bChecked)
			rBtn.OffsetRect(1, 1);

		CFont* pOld = NULL;
		
		if (eb.hFont)
			pOld = pDC->SelectObject(CFont::FromHandle(eb.hFont));
		else
		{
			CFont* pFont = GetFont();
			pOld = (CFont*)pDC->SelectObject(pFont);
		}
		
		pDC->SetTextAlign((eb.bSymbol ? TA_LEFT : TA_CENTER) | TA_TOP);
		pDC->SetBkMode(TRANSPARENT);
		
		int nCharHeight = pDC->GetTextExtent("A").cy;
		int nVOffset = ((rBtn.Height() - nCharHeight + 1) / 2) - (bThemed ? 0 : 1);
		int nHOffset = eb.bSymbol ? -2 : (rBtn.Width() + 1) / 2;

		// if the button has a drop menu position the text in the 
		// center of what remains
		if (eb.bDropMenu)
			nHOffset = (rBtn.Width() - MENUSIZE + 4) / 2; 

		CPoint ptText(rBtn.left + nHOffset, rBtn.top + nVOffset);
		DrawEnabledText(pDC, ptText, eb.sCaption, rBtn, bEnabled, eb.bSymbol);

		// cleanup
		if (pOld)
			pDC->SelectObject(pOld);
	}

	pDC->RestoreDC(nSaveDC);
}
Exemplo n.º 9
0
void CToolTipCtrlX::CustomPaint(LPNMTTCUSTOMDRAW pNMCD)
{
	CWnd* pwnd = CWnd::FromHandle(pNMCD->nmcd.hdr.hwndFrom);
	CDC* pdc = CDC::FromHandle(pNMCD->nmcd.hdc);

	// Windows Vista (General)
	// -----------------------
	// *Need* to use (some aspects) of the 'TOOLTIP' theme to get typical Vista tooltips.
	//
	// Windows Vista *without* SP1
	// ---------------------------
	// The Vista 'TOOLTIP' theme offers a bold version of the standard tooltip font via 
	// the TTP_STANDARDTITLE part id. Furthermore TTP_STANDARDTITLE is the same font as
	// the standard tooltip font (TTP_STANDARD). So, the 'TOOLTIP' theme can get used
	// thoroughly.
	//
	// Windows Vista *with* SP1
	// ------------------------
	// The Vista SP1(!) 'TOOLTIP' theme does though *not* offer a bold font. Keep
	// in mind that TTP_STANDARDTITLE does not return a bold font. Keep also in mind
	// that TTP_STANDARDTITLE is even a *different* font than TTP_STANDARD!
	// Which means, that TTP_STANDARDTITLE should *not* be used within the same line
	// as TTP_STANDARD. It just looks weird. TTP_STANDARDTITLE could be used for a
	// single line (the title line), but it would though not give us a bold font.
	// So, actually we can use the Vista 'TOOLTIP' theme only for getting the proper
	// tooltip background.
	//
	// Windows XP
	// ----------
	// Can *not* use the 'TOOLTIP' theme at all because it would give us only a (non-bold)
	// black font on a white tooltip window background. Seems that the 'TOOLTIP' theme under 
	// WinXP is just using the default Window values (black+white) and does not
	// use any of the tooltip specific Window metrics...
	//
	bool bUseEmbeddedThemeFonts = false;
	HTHEME hTheme = NULL;
	if (theApp.IsVistaThemeActive()) {
		hTheme = OpenThemeData(*pwnd, L"TOOLTIP");
		// Using the theme's fonts works only under Vista without SP1. When SP1
		// is installed the fonts which are used for TTP_STANDARDTITLE and TTP_STANDARD
		// do no longer match (should not get displayed within the same text line).
		if (hTheme) bUseEmbeddedThemeFonts = true;
	}

	CString strText;
	pwnd->GetWindowText(strText);

	CRect rcWnd;
	pwnd->GetWindowRect(&rcWnd);

	CFont* pOldDCFont = NULL;
	if (hTheme == NULL || !bUseEmbeddedThemeFonts)
	{
		// If we have a theme, we try to query the correct fonts from it
		if (m_fontNormal.m_hObject == NULL && hTheme) {
			// Windows Vista Ultimate, 6.0.6001 SP1 Build 6001, English with German Language Pack
			// ----------------------------------------------------------------------------------
			// TTP_STANDARD, TTSS_NORMAL
			//  Height   -12
			//  Weight   400
			//  CharSet  1
			//  Quality  5
			//  FaceName "Segoe UI"
			//
			// TTP_STANDARDTITLE, TTSS_NORMAL
			//  Height   -12
			//  Weight   400
			//  CharSet  1
			//  Quality  5
			//  FaceName "Segoe UI Fett" (!!!) Note: "Fett" (that is German !?)
			//
			// That font name ("Segoe UI *Fett*") looks quite suspicious. I would not be surprised
			// if that eventually leads to a problem within the font mapper which may not be capable
			// of finding the (english) version of that font and thus falls back to the standard
			// system font. At least this would explain why the TTP_STANDARD and TTP_STANDARDTITLE
			// fonts are *different* on that particular Windows Vista system.
			LOGFONT lf = {0};
			if (GetThemeFont(hTheme, pdc->m_hDC, TTP_STANDARD, TTSS_NORMAL, TMT_FONT, &lf) == S_OK) {
				VERIFY( m_fontNormal.CreateFontIndirect(&lf) );

				if (m_bCol1Bold && m_fontBold.m_hObject == NULL) {
					memset(&lf, 0, sizeof(lf));
					if (GetThemeFont(hTheme, pdc->m_hDC, TTP_STANDARDTITLE, TTSS_NORMAL, TMT_FONT, &lf) == S_OK)
						VERIFY( m_fontBold.CreateFontIndirect(&lf) );
				}

				// Get the tooltip font color
				COLORREF crText;
				if (GetThemeColor(hTheme, TTP_STANDARD, TTSS_NORMAL, TMT_TEXTCOLOR, &crText) == S_OK)
					m_crTooltipTextColor = crText;
			}
		}

		// If needed, create the standard tooltip font which was queried from the system metrics
		if (m_fontNormal.m_hObject == NULL && m_lfNormal.lfHeight != 0)
			VERIFY( m_fontNormal.CreateFontIndirect(&m_lfNormal) );

		// Select the tooltip font
		if (m_fontNormal.m_hObject != NULL) {
			pOldDCFont = pdc->SelectObject(&m_fontNormal);

			// If needed, create the bold version of the tooltip font by deriving it from the standard font
			if (m_bCol1Bold && m_fontBold.m_hObject == NULL) {
				LOGFONT lf;
				m_fontNormal.GetLogFont(&lf);
				lf.lfWeight = FW_BOLD;
				VERIFY( m_fontBold.CreateFontIndirect(&lf) );
			}
		}

		// Set the font color (queried from system metrics or queried from theme)
		pdc->SetTextColor(m_crTooltipTextColor);
	}

	// Auto-format the text only if explicitly requested. Otherwise we would also format
	// single line tooltips for regular list items, and if those list items contain ':'
	// characters they would be shown partially in bold. For performance reasons, the
	// auto-format is to be requested by appending the TOOLTIP_AUTOFORMAT_SUFFIX_CH 
	// character. Appending, because we can remove that character efficiently without
	// re-allocating the entire string.
	bool bAutoFormatText = strText.GetLength() > 0 && strText[strText.GetLength() - 1] == TOOLTIP_AUTOFORMAT_SUFFIX_CH;
	if (bAutoFormatText)
		strText.Truncate(strText.GetLength() - 1); // truncate the TOOLTIP_AUTOFORMAT_SUFFIX_CH char by setting it to NUL
	bool bShowFileIcon = m_bShowFileIcon && bAutoFormatText;
	if (bShowFileIcon) {
		int iPosNL = strText.Find(_T('\n'));
		if (iPosNL > 0) {
			int iPosColon = strText.Find(_T(':'));
			if (iPosColon < iPosNL)
				bShowFileIcon = false; // 1st line does not contain a filename
		}
	}
	
	int iTextHeight = 0;
	int iMaxCol1Width = 0;
	int iMaxCol2Width = 0;
	int iMaxSingleLineWidth = 0;
	CSize sizText(0);
	int iPos = 0;
	int iCaptionHeight = 0;
	const int iCaptionEnd = bShowFileIcon ? max(strText.Find(_T("\n<br_head>\n")), 0) : 0; // special tooltip with file icon
	const int iLineHeightOff = 1;
	const int iIconMinYBorder = bShowFileIcon ? 3 : 0;
	const int iIconWidth = bShowFileIcon ? theApp.GetBigSytemIconSize().cx : 0;
	const int iIconHeight = bShowFileIcon ? theApp.GetBigSytemIconSize().cy : 0;
	const int iIconDrawingWidth = bShowFileIcon ? (iIconWidth + 9) : 0;
	while (iPos != -1)
	{
		CString strLine = GetNextString(strText, _T('\n'), iPos);
		int iColon = bAutoFormatText ? strLine.Find(_T(':')) : -1;
		if (iColon != -1) {
			CSize siz;
			if (hTheme && bUseEmbeddedThemeFonts) {
				CRect rcExtent;
				CRect rcBounding(0, 0, 32767, 32767);
				GetThemeTextExtent(hTheme, *pdc, m_bCol1Bold ? TTP_STANDARDTITLE : TTP_STANDARD, TTSS_NORMAL, strLine, iColon + 1, m_dwCol1DrawTextFlags, &rcBounding, &rcExtent);
				siz.cx = rcExtent.Width();
				siz.cy = rcExtent.Height();
			}
			else {
				CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
				siz = pdc->GetTextExtent(strLine, iColon + 1);
				if (pOldFont)
					pdc->SelectObject(pOldFont);
			}
			iMaxCol1Width = max<int>(iMaxCol1Width, siz.cx + ((bShowFileIcon && iPos <= iCaptionEnd + strLine.GetLength()) ? iIconDrawingWidth : 0));
			iTextHeight = siz.cy + iLineHeightOff; // update height with 'col1' string, because 'col2' string might be empty and therefore has no height
			if (iPos <= iCaptionEnd)
				iCaptionHeight += siz.cy + iLineHeightOff;
			else
				sizText.cy += siz.cy + iLineHeightOff;

			LPCTSTR pszCol2 = (LPCTSTR)strLine + iColon + 1;
			while (_istspace((_TUCHAR)*pszCol2))
				pszCol2++;
			if (*pszCol2 != _T('\0')) {
				if (hTheme && bUseEmbeddedThemeFonts) {
					CRect rcExtent;
					CRect rcBounding(0, 0, 32767, 32767);
					GetThemeTextExtent(hTheme, *pdc, TTP_STANDARD, TTSS_NORMAL, pszCol2, ((LPCTSTR)strLine + strLine.GetLength()) - pszCol2, m_dwCol2DrawTextFlags, &rcBounding, &rcExtent);
					siz.cx = rcExtent.Width();
					siz.cy = rcExtent.Height();
				}
				else {
					siz = pdc->GetTextExtent(pszCol2, ((LPCTSTR)strLine + strLine.GetLength()) - pszCol2);
				}
				iMaxCol2Width = max<int>(iMaxCol2Width, siz.cx);
			}
		}
		else if (bShowFileIcon && iPos <= iCaptionEnd && iPos == strLine.GetLength() + 1){
			// file name, printed bold on top without any tabbing or desc
			CSize siz;
			if (hTheme && bUseEmbeddedThemeFonts) {
				CRect rcExtent;
				CRect rcBounding(0, 0, 32767, 32767);
				GetThemeTextExtent(hTheme, *pdc, m_bCol1Bold ? TTP_STANDARDTITLE : TTP_STANDARD, TTSS_NORMAL, strLine, strLine.GetLength(), m_dwCol1DrawTextFlags, &rcBounding, &rcExtent);
				siz.cx = rcExtent.Width();
				siz.cy = rcExtent.Height();
			}
			else {
				CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
				siz = pdc->GetTextExtent(strLine);
				if (pOldFont)
					pdc->SelectObject(pOldFont);
			}
			iMaxSingleLineWidth = max<int>(iMaxSingleLineWidth, siz.cx + iIconDrawingWidth);
			iCaptionHeight += siz.cy + iLineHeightOff;
		}
		else if (!strLine.IsEmpty() && strLine.Compare(_T("<br>")) != 0 && strLine.Compare(_T("<br_head>")) != 0) {
			CSize siz;
			if (hTheme && bUseEmbeddedThemeFonts) {
				CRect rcExtent;
				CRect rcBounding(0, 0, 32767, 32767);
				GetThemeTextExtent(hTheme, *pdc, TTP_STANDARD, TTSS_NORMAL, strLine, strLine.GetLength(), m_dwCol2DrawTextFlags, &rcBounding, &rcExtent);
				siz.cx = rcExtent.Width();
				siz.cy = rcExtent.Height();
			}
			else {
				siz = pdc->GetTextExtent(strLine);
			}
			iMaxSingleLineWidth = max<int>(iMaxSingleLineWidth, siz.cx + ((bShowFileIcon && iPos <= iCaptionEnd) ? iIconDrawingWidth : 0));
			if (bShowFileIcon && iPos <= iCaptionEnd + strLine.GetLength())
				iCaptionHeight += siz.cy + iLineHeightOff;
			else
				sizText.cy += siz.cy + iLineHeightOff;
		}
		else{
			CSize siz;
			if (hTheme && bUseEmbeddedThemeFonts) {
				CRect rcExtent;
				CRect rcBounding(0, 0, 32767, 32767);
				GetThemeTextExtent(hTheme, *pdc, TTP_STANDARD, TTSS_NORMAL, _T(" "), 1, m_dwCol2DrawTextFlags, &rcBounding, &rcExtent);
				siz.cx = rcExtent.Width();
				siz.cy = rcExtent.Height();
			}
			else {
				// TODO: Would need to use 'GetTabbedTextExtent' here, but do we actually use 'tabbed' text here at all ??
				siz = pdc->GetTextExtent(_T(" "), 1);
			}
			sizText.cy += siz.cy + iLineHeightOff;
		}
	}
	if (bShowFileIcon && iCaptionEnd > 0)
		iCaptionHeight = max<int>(iCaptionHeight, theApp.GetBigSytemIconSize().cy + (2*iIconMinYBorder));
	sizText.cy += iCaptionHeight;
	if (hTheme && theApp.m_ullComCtrlVer >= MAKEDLLVERULL(6,16,0,0))
		sizText.cy += 2; // extra bottom margin for Vista/Theme

	iMaxCol1Width = min(m_iScreenWidth4, iMaxCol1Width);
	iMaxCol2Width = min(m_iScreenWidth4*2, iMaxCol2Width);

	const int iMiddleMargin = 6;
	iMaxSingleLineWidth = max(iMaxSingleLineWidth, iMaxCol1Width + iMiddleMargin + iMaxCol2Width);
	if (iMaxSingleLineWidth > m_iScreenWidth4*3)
		iMaxSingleLineWidth = m_iScreenWidth4*3;
	sizText.cx = iMaxSingleLineWidth;

	if (pNMCD->uDrawFlags & DT_CALCRECT)
	{
		pNMCD->nmcd.rc.left = rcWnd.left;
		pNMCD->nmcd.rc.top = rcWnd.top;
		pNMCD->nmcd.rc.right = rcWnd.left + sizText.cx;
		pNMCD->nmcd.rc.bottom = rcWnd.top + sizText.cy;
	}
	else
	{
		pwnd->ScreenToClient(&rcWnd);

		int iOldBkColor = -1;
		if (hTheme) {
			int iPartId = TTP_STANDARD;
			int iStateId = TTSS_NORMAL;
			if (IsThemeBackgroundPartiallyTransparent(hTheme, iPartId, iStateId))
				DrawThemeParentBackground(m_hWnd, pdc->m_hDC, &rcWnd);
			DrawThemeBackground(hTheme, pdc->m_hDC, iPartId, iStateId, &rcWnd, NULL);
		}
		else {
			::FillRect(*pdc, &rcWnd, GetSysColorBrush(COLOR_INFOBK));
			iOldBkColor = pdc->SetBkColor(m_crTooltipBkColor);
			// Vista: Need to draw the window border explicitly !?
			if (theApp.m_ullComCtrlVer >= MAKEDLLVERULL(6,16,0,0)) {
				CPen pen;
				pen.CreatePen(0, 1, m_crTooltipTextColor);
				CPen *pOP = pdc->SelectObject(&pen);
				pdc->MoveTo(rcWnd.left, rcWnd.top);
				pdc->LineTo(rcWnd.right - 1, rcWnd.top);
				pdc->LineTo(rcWnd.right - 1, rcWnd.bottom - 1);
				pdc->LineTo(rcWnd.left, rcWnd.bottom - 1);
				pdc->LineTo(rcWnd.left, rcWnd.top);
				pdc->SelectObject(pOP);
				pen.DeleteObject();
			}
		}

		int iOldBkMode = 0;
		if ((hTheme && !bUseEmbeddedThemeFonts) || (hTheme == NULL && iOldBkColor != -1))
			iOldBkMode = pdc->SetBkMode(TRANSPARENT);

		CPoint ptText(pNMCD->nmcd.rc.left, pNMCD->nmcd.rc.top);
		iPos = 0;
		while (iPos != -1)
		{
			CString strLine = GetNextString(strText, _T('\n'), iPos);
			int iColon = bAutoFormatText ? strLine.Find(_T(':')) : -1;
			CRect rcDT;
			if (!bShowFileIcon || (unsigned)iPos > (unsigned)iCaptionEnd + strLine.GetLength())
				rcDT.SetRect(ptText.x, ptText.y, ptText.x + iMaxCol1Width, ptText.y + iTextHeight);
			else
				rcDT.SetRect(ptText.x + iIconDrawingWidth, ptText.y, ptText.x + iMaxCol1Width, ptText.y + iTextHeight);
			if (iColon != -1) {
				// don't draw empty <col1> strings (they are still handy to use for skipping the <col1> space)
				if (iColon > 0) {
					if (hTheme && bUseEmbeddedThemeFonts)
						DrawThemeText(hTheme, pdc->m_hDC, m_bCol1Bold ? TTP_STANDARDTITLE : TTP_STANDARD, TTSS_NORMAL, strLine, iColon + 1, m_dwCol1DrawTextFlags, 0, &rcDT);
					else {
						CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
						pdc->DrawText(strLine, iColon + 1, &rcDT, m_dwCol1DrawTextFlags);
						if (pOldFont)
							pdc->SelectObject(pOldFont);
					}
				}

				LPCTSTR pszCol2 = (LPCTSTR)strLine + iColon + 1;
				while (_istspace((_TUCHAR)*pszCol2))
					pszCol2++;
				if (*pszCol2 != _T('\0')) {
					rcDT.left = ptText.x + iMaxCol1Width + iMiddleMargin;
					rcDT.right = rcDT.left + iMaxCol2Width;
					if (hTheme && bUseEmbeddedThemeFonts)
						DrawThemeText(hTheme, pdc->m_hDC, TTP_STANDARD, TTSS_NORMAL, pszCol2, ((LPCTSTR)strLine + strLine.GetLength()) - pszCol2, m_dwCol2DrawTextFlags, 0, &rcDT);
					else
						pdc->DrawText(pszCol2, ((LPCTSTR)strLine + strLine.GetLength()) - pszCol2, &rcDT, m_dwCol2DrawTextFlags);
				}

				ptText.y += iTextHeight;
			}
			else if (bShowFileIcon && iPos <= iCaptionEnd && iPos == strLine.GetLength() + 1){
				// first line on special fileicon tab - draw icon and bold filename
				if (hTheme && bUseEmbeddedThemeFonts)
					DrawThemeText(hTheme, pdc->m_hDC, m_bCol1Bold ? TTP_STANDARDTITLE : TTP_STANDARD, TTSS_NORMAL, strLine, strLine.GetLength(), m_dwCol1DrawTextFlags, 0, &CRect(ptText.x  + iIconDrawingWidth, ptText.y, ptText.x + iMaxSingleLineWidth, ptText.y + iTextHeight));
				else {
					CFont* pOldFont = m_bCol1Bold ? pdc->SelectObject(&m_fontBold) : NULL;
					pdc->DrawText(strLine, CRect(ptText.x  + iIconDrawingWidth, ptText.y, ptText.x + iMaxSingleLineWidth, ptText.y + iTextHeight), m_dwCol1DrawTextFlags);
					if (pOldFont)
						pdc->SelectObject(pOldFont);
				}

				ptText.y += iTextHeight;
				int iImage = (int) theApp.GetFileTypeSystemImageIdx(strLine, -1, true);
				if (theApp.GetBigSystemImageList() != NULL) {
					int iPosY = rcDT.top;
					if (iCaptionHeight > iIconHeight)
						iPosY += (iCaptionHeight - iIconHeight) / 2;
					::ImageList_Draw(theApp.GetBigSystemImageList(), iImage, pdc->GetSafeHdc(), ptText.x, iPosY, ILD_TRANSPARENT);
				}
			}
			else {
				bool bIsBrHeadLine = false;
				if (bAutoFormatText && (strLine.Compare(_T("<br>")) == 0 || (bIsBrHeadLine = strLine.Compare(_T("<br_head>")) == 0) == true)){
					CPen pen;
					pen.CreatePen(0, 1, m_crTooltipTextColor);
					CPen *pOP = pdc->SelectObject(&pen);
					if (bIsBrHeadLine)
						ptText.y = iCaptionHeight;
					pdc->MoveTo(ptText.x, ptText.y + ((iTextHeight - 2) / 2)); 
					pdc->LineTo(ptText.x + iMaxSingleLineWidth, ptText.y + ((iTextHeight - 2) / 2));
					ptText.y += iTextHeight;
					pdc->SelectObject(pOP);
					pen.DeleteObject();
				}
				else{
					if (hTheme && bUseEmbeddedThemeFonts) {
						CRect rcLine(ptText.x, ptText.y, 32767, 32767);
						DrawThemeText(hTheme, pdc->m_hDC, TTP_STANDARD, TTSS_NORMAL, strLine, strLine.GetLength(), DT_EXPANDTABS | m_dwCol2DrawTextFlags, 0, &rcLine);
						ptText.y += iTextHeight;
					}
					else {
						// Text is written in the currently selected font. If 'nTabPositions' is 0 and 'lpnTabStopPositions' is NULL,
						// tabs are expanded to eight times the average character width.
						CSize siz;
						if (strLine.IsEmpty()) // Win98: To draw an empty line we need to output at least a space.
							siz = pdc->TabbedTextOut(ptText.x, ptText.y, _T(" "), 1, NULL, 0);
						else
							siz = pdc->TabbedTextOut(ptText.x, ptText.y, strLine, strLine.GetLength(), NULL, 0);
						ptText.y += siz.cy + iLineHeightOff;
					}
				}
			}
		}
		if (iOldBkColor != -1)
			pdc->SetBkColor(iOldBkColor);
		if (hTheme && !bUseEmbeddedThemeFonts)
			pdc->SetBkMode(iOldBkMode);
	}
	if (pOldDCFont)
		pdc->SelectObject(pOldDCFont);
	if (hTheme)
		CloseThemeData(hTheme);
}