我最近刚开始使用FreeType库,并开始尝试从缓冲区复制到directx9纹理。
我现在正在收到双字母,尽管从通过加载单个字符创建的缓冲区中复制了如下:
[字符'a'的复制尝试]
以下是我目前的代码:
void TexFont::freeTypeSave()
{
static FT_Library library; /* handle to library */
static FT_Face face; /* handle to face object */
if (FT_Init_FreeType(&library)) {
NHelper::OutputDebugStringN("error");
}
if (FT_New_Face(library,TEXT("Fonts\\arial.ttf"),0,&face)) {
NHelper::OutputDebugStringN("font load failed\n");
}
else {
//NHelper::OutputDebugStringN("font faces: %d \n", face->num_faces);
}
static int error;
static UINT width, height;
static int mTtfSize = 64;
static int mTtfResolution = 96;
static IDirect3DTexture9* mTexture;
static unsigned int mPixelBytes = 2;
static unsigned int mDataSize = width * height * mPixelBytes;
// size settings (convert font size to *64)
FT_F26Dot6 ftSize = (FT_F26Dot6)(mTtfSize * (1 << 6));
error=FT_Set_Char_Size(face, ftSize, 0, mTtfResolution, mTtfResolution);
// load glyph + render
error = FT_Load_Char( face, L'a', FT_LOAD_RENDER );
if (error)
NHelper::OutputDebugStringN("could not load char");
// start copy procedure
width = face->glyph->bitmap.width;
height = face->glyph->bitmap.rows;
D3DXCreateTexture(
g_engine->getDevice(),
width, height,
1, 0,
D3DFMT_A8L8, D3DPOOL_MANAGED,
&mTexture);
D3DLOCKED_RECT lockedRect;
mTexture->LockRect(0, &lockedRect,0, 0);
unsigned char* pSrcPixels = face->glyph->bitmap.buffer;
unsigned char* pDestPixels = (unsigned char*)lockedRect.pBits;
for(UINT i = 0; i < height; ++i)
{
//copy a row
memcpy(pDestPixels, pSrcPixels, width * 2); //2 bytes per pixel (1byte alpha, 1byte greyscale)
//advance row pointers
pSrcPixels += face->glyph->bitmap.pitch;
pDestPixels += lockedRect.Pitch;
}
NHelper::OutputDebugStringN("char width: %d, height: %d \n", width, height);
mTexture->UnlockRect(0);
D3DXSaveTextureToFileA("test.png",D3DXIFF_PNG, mTexture, 0);
// release face
FT_Done_Face(face);
// library shutdown
FT_Done_FreeType(library);
}
关于发生了什么以及如何解决这个问题的任何想法?
注意:更改字体大小只会创建更大的图像。我仍然得到相同的结果。
- 更新 -
尝试Drop的建议,我尝试更改memcpy(pDestPixels, pSrcPixels, width * 2);
到memcpy(pDestPixels, pSrcPixels, width * 1);
它返回以下内容:
图像左侧有一个字形,但图像大小相同。 (字形只占用图像空间的一半)
答案 0 :(得分:1)
您将字符加载为
FT_Load_Char( face, L'a', FT_LOAD_RENDER );
这意味着that
默认情况下,字形以 FT_RENDER_MODE_NORMAL 模式呈现
和
FT_RENDER_MODE_NORMAL 这是默认的渲染模式;它对应于8位抗锯齿位图。
但你复制为16位:
memcpy(pDestPixels, pSrcPixels, width * 2); //2 bytes per pixel (1byte alpha, 1byte greyscale)
你真的不需要在任何角色中使用灰度组件来进行正确的渲染(你只需要知道必须为这个像素应用颜色和多少)。因此,在加载时将所有字符设为8位掩码。
然后在渲染之前转换为32位图像:在RGB
组件中应用颜色并将掩码设置为A
组件。我是用着色器做的。
希望它有所帮助。快乐的编码!
更新1
由于现在您正在复制8位源,memcpy
每像素8位,显然您还需要将目标(mTexture
)调整为每像素相同位:{{ 1}}(8位)而不是D3DFMT_A8
(8 + 8 = 16位)。