You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

126 lines
3.3 KiB
C++

#include "StdAfx.h"
#include "FontTrueType.h"
#include "LogMgr.h"
vector<CString> TrueTypeVec;//用来读取字体的容器
/*回调函数,枚举系统已经安装的字体*/
BOOL CALLBACK EnumWinFontCallBackEx(ENUMLOGFONTEX* pelf, NEWTEXTMETRICEX* lpntm, int FontType, LPVOID pThis)
{
if(FontType&RASTER_FONTTYPE)
{
return TRUE;
}
CString str;
if (FontType&TRUETYPE_FONTTYPE)
{
str=((pelf)->elfLogFont.lfFaceName);
}
TrueTypeVec.push_back(str);
return TRUE;
}
CFontTrueType::CFontTrueType(void)
{
}
CFontTrueType::~CFontTrueType(void)
{
}
void CFontTrueType::Initialize()
{
HDC hDC;
hDC=::GetWindowDC(NULL);
LOGFONT lf;
memset(&lf,0,sizeof(LOGFONT));
lf.lfCharSet=GB2312_CHARSET;
::EnumFontFamiliesEx(hDC, &lf,(FONTENUMPROC)EnumWinFontCallBackEx,(LPARAM)this,(DWORD) 0);
::ReleaseDC(NULL,hDC);
//导出临时容器
int size = TrueTypeVec.size();
for(int i=0;i<size;i++)
{
CString str = TrueTypeVec[i].Left(1);
if(str!=_T("@"))//删除@ 开头的字体
{
AddTypeName(TrueTypeVec[i]);
}
}
}
void CFontTrueType::CreatCharVec(char *pChar,vector<PointType> &PonitVec)
{
CClientDC dc(NULL);
CDC *pDC = &dc;
LOGFONT lf;
memset(&lf, 0, sizeof(lf));
lf.lfHeight = 1000;//尺寸越大线条平滑度越好
lf.lfWeight = FW_NORMAL;
lf.lfOutPrecision = OUT_TT_ONLY_PRECIS;
lf.lfCharSet = GB2312_CHARSET;
//字体名字
_tcscpy(lf.lfFaceName, _T(GetCurFontName()));
// create and select it
CFont newFont;
if (!newFont.CreateFontIndirect(&lf))
return;
CFont* pOldFont = pDC->SelectObject(&newFont);
pDC->SetBkMode(TRANSPARENT);//背景透明
//开始一个路径
pDC->BeginPath();
pDC->TextOut(0, 0, pChar);
pDC->EndPath();//结束路径
//将曲线转化为线段输出
pDC->FlattenPath();//将一个路径中的所有曲线都转换成线段
int Count=pDC->GetPath(NULL,NULL,0);//获取路径顶点数
CPoint* pPoin=new CPoint[Count];
BYTE* pByte=new BYTE[Count];
CPoint endpoint;
pDC->GetPath(pPoin,pByte,Count);
PointType PointData;
for(int i=0;i<Count;i++)
{
//按点绘制
switch(pByte[i])
{
case PT_MOVETO:
PointData.first.x = pPoin[i].x;
PointData.first.y = pPoin[i].y;
PointData.second = true;
PonitVec.push_back(PointData);
endpoint=pPoin[i];
break;
case PT_LINETO:
PointData.first.x = pPoin[i].x;
PointData.first.y = pPoin[i].y;
PointData.second = false;
PonitVec.push_back(PointData);
break;
case PT_LINETO|PT_CLOSEFIGURE://闭合曲线
PointData.first.x = endpoint.x;
PointData.first.y = endpoint.y;
PointData.second = false;
PonitVec.push_back(PointData);
break;
}
}
delete[] pPoin;
delete[] pByte;
pDC->SelectObject(pOldFont);
//垂直镜像数据
Mirror(PonitVec);
}
//垂直镜像数据
void CFontTrueType::Mirror(vector<PointType> &PonitVec)
{
int size = PonitVec.size();
for(int i=0;i<size;i++)
{
PonitVec[i].first.y = PonitVec[i].first.y+(0-PonitVec[i].first.y)*2;
}
}