GDI绘制文字的时候,如何实现部分字体特殊处理

凌乱哥 2018-06-29 10:17:00
用DrawText绘制文字,但是想把其中2处的若干文字重点标注一下,采用加粗、变色、下划线类似的处理,该怎么实现

举个例子比如:
GDI绘制文字的时候,如何实现部分字体特殊处理

GDI不行的话GDI+也行
...全文
612 13 打赏 收藏 转发到动态 举报
写回复
用AI写文章
13 条回复
切换为时间正序
请发表友善的回复…
发表回复
hhhh63 2018-07-27
  • 打赏
  • 举报
回复
换个控件吧,RichText
赵4老师 2018-07-03
  • 打赏
  • 举报
回复
引用 10 楼 bigtree_mfc 的回复:
要不自己写个输出类,封装下上面的,以后都能用

过早的优化是万恶之源。
大树学长 2018-07-02
  • 打赏
  • 举报
回复
要不自己写个输出类,封装下上面的,以后都能用
worldy 2018-07-02
  • 打赏
  • 举报
回复
创建多个不同的字符Font,根据需要选用
paschen 2018-06-29
  • 打赏
  • 举报
回复
字体不同的要分开输出 设置输出字体(包括是否下划线): HGDIOBJ hFont = GetStockObject(DEFAULT_GUI_FONT); LOGFONT lf; GetObject(hFont, (int)sizeof(LOGFONT), (LPVOID)&lf); //这里得到的是默认的系统字体,可在此基础上调整,如 lf.lfUnderline = 1; //显示下划线 HFONT hNewFont = CreateFontIndirect(&lf); //DrawText后需要DeleteObject((HGDIOBJ)hNewFont); DeleteObject(hFont); 设置颜色: SetTextColor(hDC, RGB(255, 255, 255); //这里设置为白色 确定输出位置,由于是分开输出,DrawText需要用DT_CALCRECT标记,这样会返回本次文字实际输出的矩形位置,由此可确定下一次文字输出的位置
zgl7903 2018-06-29
  • 打赏
  • 举报
回复

void CSDI6View::OnDraw(CDC* pDC)
{
CSDI6Doc* pDoc = GetDocument();
ASSERT_VALID(pDoc);
// TODO: add draw code for native data here

int nSaveDC = pDC->SaveDC();

//获取客户区坐标
CRect rcClient;
GetClientRect(&rcClient);

//填充背景色
pDC->FillSolidRect(rcClient, RGB(255, 255, 255));

//设置背景透明
int OldBkMode = pDC->SetBkMode(TRANSPARENT);

LOGFONT logFont = {0};
_tcscpy_s(logFont.lfFaceName, _T("Airal"));

//修改字体大小
logFont.lfHeight = -MulDiv(72, pDC->GetDeviceCaps(LOGPIXELSY), 72);
logFont.lfUnderline = 0; //无下划线
logFont.lfWeight = FW_NORMAL;

CFont NormalFont;
NormalFont.CreatePointFontIndirect(&logFont);

logFont.lfUnderline = 1; //带下划线
logFont.lfWeight = FW_HEAVY; //加黑
logFont.lfItalic = TRUE; //斜体
CFont UnderLineFont;
UnderLineFont.CreatePointFontIndirect(&logFont);

//选入常规字体
CFont *pOldFont = pDC->SelectObject(&NormalFont);
//设置字体颜色黑色
COLORREF OldtxtColor = pDC->SetTextColor(RGB(0, 0,0));

TEXTMETRIC txtMetric;
pDC->GetTextMetrics(&txtMetric);

int sx = 10, sy = 10;

{
CString szStr = _T("一般字体");
pDC->SelectObject(&NormalFont);
pDC->SetTextColor(RGB(0, 0,0));
CRect rcTxt(sx, sy, rcClient.bottom, rcClient.right);
pDC->DrawText(szStr, rcTxt, DT_LEFT|DT_TOP);
pDC->DrawText(szStr, rcTxt, DT_LEFT|DT_TOP|DT_CALCRECT);
sx += rcTxt.Width();
}
{
CString szStr = _T("红色带下划线字体");
pDC->SelectObject(&UnderLineFont);
pDC->SetTextColor(RGB(255, 0, 0));
CRect rcTxt(sx, sy, rcClient.bottom, rcClient.right);
pDC->DrawText(szStr, rcTxt, DT_LEFT|DT_TOP);
pDC->DrawText(szStr, rcTxt, DT_LEFT|DT_TOP|DT_CALCRECT);
sx += rcTxt.Width();
}

//结束清理
pDC->SetTextColor(OldtxtColor);
pDC->SelectObject(pOldFont);
pDC->SetBkMode(OldBkMode);
pDC->RestoreDC(nSaveDC);

}

zgl7903 2018-06-29
  • 打赏
  • 举报
回复
每个字单独分开来输出
SetTextColor 修改字体颜色
修改字体属性 LOGFONT 中的 lfUnderline 就是下划线

凌乱哥 2018-06-29
  • 打赏
  • 举报
回复
引用 5 楼 oblivi 的回复:
你这个效果不错,我先研究一下
凌乱哥 2018-06-29
  • 打赏
  • 举报
回复
引用 1 楼 zgl7903 的回复:
每个字单独分开来输出


引用 3 楼 paschen 的回复:
字体不同的要分开输出


引用 4 楼 schlafenhamster 的回复:
2楼代码 可行

因为你们的方法是一样的,我统一回复一下:
这样可行,但是考虑到实际项目还有多语言的情况,就变得复杂了。。。
oblivi 2018-06-29
  • 打赏
  • 举报
回复
	CRect rect;
GetClientRect(hWnd, rect);
HDC hdc = GetDC(hWnd);
HDC memDC = CreateCompatibleDC(hdc);

BITMAPINFO bmi;
bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
bmi.bmiHeader.biBitCount = 32;
bmi.bmiHeader.biHeight = rect.Height();
bmi.bmiHeader.biWidth = rect.Width();
bmi.bmiHeader.biPlanes = 1;
bmi.bmiHeader.biCompression = BI_RGB;
bmi.bmiHeader.biClrImportant = 0;
bmi.bmiHeader.biClrUsed = 0;
bmi.bmiHeader.biXPelsPerMeter = 0;
bmi.bmiHeader.biYPelsPerMeter = 0;
bmi.bmiHeader.biSizeImage = rect.Width()*rect.Height() * 32 / 8;

HBITMAP bmp = CreateDIBSection(hdc, &bmi, 0, NULL, NULL, 0);
SelectObject(memDC, bmp);

Gdiplus::Graphics *graphics = new Gdiplus::Graphics(memDC);
graphics->SetSmoothingMode(Gdiplus::SmoothingModeAntiAlias);
graphics->SetTextRenderingHint(Gdiplus::TextRenderingHintAntiAlias);

#ifdef _UNICODE
LPWSTR str = (LPWSTR)_lyric;
#else
USES_CONVERSION;
LPWSTR str = A2W(_lyric);
#endif // _UNICODE
Gdiplus::FontFamily fontFamily(L"微软雅黑");
Gdiplus::Font m_pFont(&fontFamily, 48, Gdiplus::FontStyleRegular, Gdiplus::UnitPixel);
Gdiplus::Font m_pFont2(&fontFamily, 48, Gdiplus::FontStyleUnderline, Gdiplus::UnitPixel);//下划线

Gdiplus::StringFormat format;
RectF layoutRect(0, 0, 1000, 100);
RectF boundingBox;
StringFormat strfmt;
strfmt.SetTrimming(StringTrimmingWord);
strfmt.SetFormatFlags(StringFormatFlagsNoWrap);
strfmt.SetLineAlignment(StringAlignmentCenter);
strfmt.SetAlignment(StringAlignmentCenter);
graphics->MeasureString(str, -1, &m_pFont, layoutRect, &strfmt, &boundingBox);


Gdiplus::GraphicsPath stringPath(FillModeAlternate);//创建路径

stringPath.AddString(str, -1, &fontFamily, m_pFont.GetStyle(), 48, boundingBox,&strfmt); //把文字加入路径

graphics->DrawPath(&Pen(Color(150,0,0,0)), &stringPath);//绘制边框

Gdiplus::LinearGradientBrush brush(boundingBox, Color::Blue, Color::Red, LinearGradientModeHorizontal);

int colors[] = { Color::Red ,Color::Orange ,Color::Yellow ,Color::Green ,Color::Cyan,Color::Blue ,Color::Purple };
REAL positions[] = { 0.0f,0.16f,0.33f,0.50f,0.67f,0.83f,1.0f };
brush.SetInterpolationColors((Color*)colors, positions, 7);
graphics->FillPath(&brush, &stringPath);//填充路径

RectF fillrect = boundingBox;
fillrect.Width = (boundingBox.Width*0.2);
stringPath.AddString(str, -1, &fontFamily, m_pFont2.GetStyle(), 48, boundingBox, &strfmt); //把文字加入路径

graphics->IntersectClip(fillrect);
graphics->FillPath(&SolidBrush(Color::Red), &stringPath);

RectF fillrect2 = boundingBox;
fillrect2.X += 500;
fillrect2.Width = (boundingBox.Width*0.2);
graphics->SetClip(fillrect2);
graphics->FillPath(&SolidBrush(Color::Green), &stringPath);

delete graphics;

BLENDFUNCTION bldfun;
bldfun.AlphaFormat = AC_SRC_ALPHA;
bldfun.BlendFlags = 0;
bldfun.BlendOp = AC_SRC_OVER;
bldfun.SourceConstantAlpha = 255;
UpdateLayeredWindow(hWnd, hdc, NULL, &CSize(1000, 100), memDC, &CPoint(0, 0), 0, &bldfun, ULW_ALPHA);

::ReleaseDC(hWnd, hdc);
::DeleteDC(memDC);
DeleteObject(bmp);
oblivi 2018-06-29
  • 打赏
  • 举报
回复
schlafenhamster 2018-06-29
  • 打赏
  • 举报
回复
2楼代码 可行
CString szStr = _T("红色带下划线字体");
pDC->SelectObject(&UnderLineFont);
pDC->SetTextColor(RGB(255, 0, 0));
CRect rcTxt(sx, sy, rcClient.bottom, rcClient.right);
pDC->DrawText(szStr, rcTxt, DT_LEFT|DT_TOP|DT_CALCRECT);
pDC->DrawText(szStr, rcTxt, DT_LEFT|DT_TOP);

红色 2句 要 上下交换一下

15,979

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC 界面
社区管理员
  • 界面
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧