快捷搜索:  as  test  1111  test aNd 8=8  test++aNd+8=8  as++aNd+8=8  as aNd 8=8

虎途国际最新网址:利用FontGen实现超小字库



曩昔也用过FontGen。不停用的是对照好的屏,以是大年夜小无所谓,字体是16X16的,也没发明问题,当我用到12X12的字体的时刻发明法度榜样照样有必然缺陷的——显示乱码。

问题出在EXFONT_draw_one_char()这个函数上。本来我做打印机的时刻也是按照这种措施。后来发明其实不可,实现繁琐,也轻易出问题。着末想象着实这便是一个单色位图的bitblt函数,就拿打印机里的一段代码改了改。

统共3个文件,此中一个是小字库的文件。

/*

* ExFont.c

*/

#include

#include

#include "ExFont.h"

int EXFONT_init(PEXFONT font,char* name, int foreground_color, int background_color,

unsigned char bk_mode, draw_pixel_func draw_pixel)

{

if(font != NULL)

{

memset(font, 0x00, sizeof(*font));

font->name = name;

font->draw_pixel = draw_pixel虎途国际最新网址;

font->foreground_color = foreground_color;

font->background_color = background_color;

font->bk_mode = bk_mode;

if(draw_pixel != NULL)

{

return 0;

}

}

return -1;

}

int EXFONT_set_thin_font_data(PEXFONT font, PEXFONT_DATA thin_font_data)

{

if(font != NULL)

{

font->thin_font_data = thin_font_data;

return 0;

}

else

{

return -1;

}

}

int EXFONT_set_wide_font_data(PEXFONT font, PEXFONT_DATA wide_font_data)

{

if(font != NULL)

{

font->wide_font_data = wide_font_data;

return 0;

}

else

{

return -1;

}

}

int EXFONT_font_index(CONST PEXFONT_DATA font_data, unsigned short cChar)

{

int low = 0;

int hign = font_data->nr;

int mid = (low + hign) / 2;

if(font_data == NULL) return -1;

if(font_data != NULL)

{

while(low items[mid].value == cChar)

{虎途国际最新网址

return mid;

}

if(font_data->items[mid].value > cChar)

{

hign = mid - 1;

}

else

{

low = mid + 1;

}

mid = (low + hign) / 2;

}

}

return -1;

}

#define BIG_ENDIAN 1

#if BIG_ENDIAN

__inline unsigned char GraphicGetPixel (char *pBuffer, int lineWidth, int x, int y)

{

int index = (y*lineWidth + x);

return ( pBuffer[index>>3] & (0x1>(7-(index & 0x07));

}

__inline void GraphicPutPixel (char *pBuffer, int lineWidth, int x, int y, unsigned char pixel)

{

int index = (y*lineWidth + x);

pBuffer[index>>3] |= (unsigned char)((unsigned char)pixel & 0x01)>3] & (0x1>(index & 0x07);

}

__inline void GraphicPutPixel (char *pBuffer, int lineWidth, int x, int y, unsigned char pixel)

{

int index = (y*lineWidth + x);

pBuffer[index>>3] |= (unsigned char)((unsigned char)pixel & 0x01)thin_font_data : font->wide_font_data;

pSrcBuff = (char *)thin_wide_font_data->items[index].data;

iSrcHeight = thin_wide_font_data->height;

iSrcWidth = thin_wide_font_data->width;

iLineWidth = (iSrcWidth&0xF8) + ((iSrcWidth&07 == 0)?0:8);

for (i=0; idraw_pixel(x+j, y+i, font->foreground_color);

}

else if(font->bk_mode == BKMODE_OPAQUE)

{

font->draw_pixel(x+j, y+i, font->background_color);

}

}

}

}

#define is_thin_char(c) (c thin_font_data : font->wide_font_data;

int w;

int h;

int max_w = x + thin_wide_font_data->width;虎途国际最新网址

int max_h = y + thin_wide_font_data->height;

unsigned char* font_data = thin_wide_font_data->items[index].data;

unsigned short i = 0;

unsigned char byte = 0;

unsigned char bit = 0;

for(h = y; h draw_pixel(w, h, font->foreground_color);

}

else if(font->bk_mode == BKMODE_OPAQUE)

{

font->draw_pixel(w, h, font->background_color);

}

if(bit == 0)

{

i++;

byte = font_data[i];

}

}

}

return;

}

int EXFONT_draw_w(CONST PEXFONT font, int x, int y, CONST wchar_t* text)

{

if(font != NULL && text != NULL)

{

unsigned short i = 0;

int index = 0;

unsigned charthin_char = 0;

int left = x;

int top = y;

while(text[i])

{

thin_char = is_thin_char(text[i]);

if(thin_char)

{

index = EXFONT_font_index(font->thin_font_data, text[i]);

if(index > font->thin_font_data->nr)

{

return -1;

}

}

else

{

index = EXFONT_font_index(font->wide_font_data, text[i]);

if(index > font->wide_font_data->nr)

{

return -1;

}

}

EXFONT_draw_one_char_new(font, left, top, index, thin_char);

//EXFONT_draw_one_char(font, left, top, index, thin_char);

left += thin_char ? font->thin_font_data->width : font->wide_font_data->width;

i++;

}

return 0;

}

else

{

return -1;

}

}

int EXFONT_draw_a(CONST PEXFONT font, int x, int y, CONST char* text)

{

if(font != NUL虎途国际最新网址L && text != NULL)

{

unsigned short i = 0;

unsigned short charContent = 0;

unsigned short index = 0;

unsigned charthin_char = 0;

int left = x;

int top = y;

while(text[i])

{

thin_char = is_thin_char((unsigned char)text[i]);

if(thin_char)

{

index = EXFONT_font_index(font->thin_font_data, text[i]);

if(index > font->thin_font_data->nr)

{

return -1;

}

i++;

}

else

{

*(char *)&charContent = text[i];

*((char *虎途国际最新网址)&charContent+1) = text[i+1];

index = EXFONT_font_index(font->wide_font_data, charContent);

if(index > font->wide_font_data->nr)

{

return -1;

}

i += 2;

}

EXFONT_draw_one_char_new(font, left, top, index, thin_char);

//EXFONT_draw_one_char(font, left, top, index, thin_char);

left += thin_char ? font->thin_font_data->width : font->wide_font_data->width;

}

return 0;

}

else

{

return -1;

}

}

PEXFONT gpCurrFont = NULL;

PEXFONT GUI_SetFont (PEXFONT pFont)

{

gpCurrFont = pFont;

}

int GUI_DrawString (int x, int y, CONST char* text)

{

if (gpCurrFont == NULL)

return -1;

if (gpCurrFont->encode == ENCODE_ANSI)

EXFONT_draw_a(gpCurrFont, x, y, text);

else

EXFONT_draw_w(gpCurrFont, x, y, (wchar_t *)text);

return 0;

}

/*

* demofont.c

*/

#include "zgr.h"

void InstallFont(draw_pixel_func my_draw_pixel)

{

//install_ansi_16x16_font(my_draw_pixel);

//install_unicode_32x32_font(my_draw_pixel);

install_unicode_16x16_font(my_draw_pixel);

install_ansi_12x12_font(my_draw_pixel);

install_ansi_16x16_font(my_draw_pixel);

}

//我是中国人透明背景不宽字符窄16x32widechar :thinabc2354465478568dfgs

#define STR_ANSI_TRANSPARENT"16x16: 宽字符 透明背景 我是中国人 thin char 123abc "

#define STR_UNICODE_TRANSPARENT L"32x32: 宽字符 透明背景 我是中国人 thin char 123abc "

#define STR_ANSI_OPAQUE"16x16: 宽字符 不透明背景 我是中国人 thin char 123abc "

#define STR_UNICODE_OPAQUE L"32x32: 宽字符 不透明背景 我是中国人 thin char 123abc"

void TestDrawText(void)

{

EXFONT_bkmode(&g_unicode_font16) = BKMODE_TRANSPARENT;

EXFONT_draw_a(&g_unicode_font16, 10, 10, STR_ANSI_TRANSPARENT);

EXFONT_bkmode(&g_unicode_font16) = BKMODE_OPAQUE;

EXFONT_draw_a(&g_unicode_font16, 10, 40, STR_ANSI_OPAQUE);

#if defined(WIN32) || defined(LINUX)

EXFONT_bkmode(&g_unicode_font16) = BKMODE_TRANSPARENT;

EXFONT_draw_w(&g_unicode_font16, 10, 80, STR_UNICODE_TRANSPARENT);

EXFONT_bkmode(&g_unicode_font16) = BKMODE_OPAQUE;

EXFONT_draw_w(&g_unicode_font16, 10, 120, STR_UNICODE_OPAQUE);

#endif

return ;

}

在字体文件中做改动

void install_ansi_16x16_font(draw_pixel_func my_draw_pixel)

{

size_t i = 0;

for(i = 0; i

#define ENCODE_ANSI0x00

#define ENCODE_UNICODE0x01

typedef struct _EXFONT {

/*

* Name of the font, used for retrieving purpose.

*/

char* name;

/*

* Background mode: BKMODE_OPAQUE or BKMODE_TRANSPARENT

*/

unsigned char bk_mode;

/*

* encode mode: BKMODE_OPAQUE or BKMODE_TRANSPARENT

*/

unsigned char encode;

/*

* Color of the char.

*/

int foreground_color;

int background_color;

/*

* Font data:

*thin_font_data: font data of ASCII chars.

*wide_font_data: font data of multibytes chars.

*/

PEXFONT_DATAthin_font_data;

PEXFONT_DATAwide_font_data;

/*

* Output function.

*/

draw_pixel_funcdraw_pixel;

}EXFONT, *PEXFONT;

这样12X12的字体能顺利显示了。结果还碰到一个很特其余问题:中翰墨符后面跟了数字,然后在接着是中文,假如数字是偶数个,后面的中文都都显示不了。

跟踪后发明,中翰墨符不是按2字节对齐有问题。着末是用逐个字节读取的措施来办理的

*(char *)&charContent = text[i];

*((char *)&charContent+1) = text[i+1];

然则留给我一个问题思虑:为什么奇数地址中读取两个字节有差错?是我硬件的问题吗?暂时办理到这里为止。

【07.05.22】

Trackback: http://tb.blog.csdn.net/TrackBack.aspx?PostId=1740032

免责声明:以上内容源自网络,版权归原作者所有,如有侵犯您的原创版权请告知,我们将尽快删除相关内容。

您可能还会对下面的文章感兴趣: