Display Truetype fonts with Win32 API

This commit is contained in:
Thomas Bernard 2018-06-22 02:15:26 +02:00
parent 486a0a09d4
commit 84fdc001cd
2 changed files with 155 additions and 2 deletions

View File

@ -438,6 +438,9 @@ void For_each_file(const char * directory_name, void Callback(const char *, cons
char search_string[MAX_PATH_CHARACTERS]; char search_string[MAX_PATH_CHARACTERS];
HANDLE h; HANDLE h;
if (Realpath(directory_name, full_filename))
_snprintf(search_string, sizeof(search_string), "%s\\*", full_filename);
else
_snprintf(search_string, sizeof(search_string), "%s\\*", directory_name); _snprintf(search_string, sizeof(search_string), "%s\\*", directory_name);
h = FindFirstFileA(search_string, &fd); h = FindFirstFileA(search_string, &fd);
if (h != INVALID_HANDLE_VALUE) if (h != INVALID_HANDLE_VALUE)

View File

@ -132,6 +132,12 @@ static void Add_font(const char *name, const char * font_name)
return; return;
#endif #endif
#if defined(WIN32) && defined(NOTTF)
// Register font in windows so they will be visible with EnumFontFamiliesEx()
if (AddFontResourceExA(name, FR_PRIVATE, 0) > 0)
return;
#endif
font = (T_Font *)malloc(sizeof(T_Font)); font = (T_Font *)malloc(sizeof(T_Font));
switch (EXTID(tolower(name[size-4]), tolower(name[size-3]), tolower(name[size-2]))) switch (EXTID(tolower(name[size-4]), tolower(name[size-3]), tolower(name[size-2])))
@ -278,6 +284,38 @@ int TrueType_font(int index)
return font->Is_truetype; return font->Is_truetype;
} }
#if defined(WIN32) && defined(NOTTF)
static int CALLBACK EnumFontFamCallback(CONST LOGFONTA *lpelf, CONST TEXTMETRICA *lpntm, DWORD FontType, LPARAM lParam)
{
T_Font * font;
if (FontType & TRUETYPE_FONTTYPE)
{
font = malloc(sizeof(T_Font));
font->Is_bitmap = 0;
font->Is_truetype = 1;
snprintf(font->Label, sizeof(font->Label), "%-17.17sTT", lpelf->lfFaceName);
font->Name = strdup(lpelf->lfFaceName);
// Gestion Liste
font->Next = NULL;
font->Previous = NULL;
// TODO insert at the right place
if (font_list_start==NULL)
{
// Premiere (liste vide)
font_list_start = font;
Nb_fonts++;
}
else
{
//font_list_start->Previous = font;
font->Next = font_list_start;
font_list_start = font;
Nb_fonts++;
}
}
return 1; // non-zero : continue enumeration
}
#endif
// Initialisation à faire une fois au début du programme // Initialisation à faire une fois au début du programme
@ -310,6 +348,18 @@ void Init_text(void)
For_each_file(directory_name, Add_font); For_each_file(directory_name, Add_font);
} }
} }
#else
{
LOGFONTA lf;
HDC dc = GetDC(NULL);
memset(&lf, 0, sizeof(lf));
lf.lfCharSet = ANSI_CHARSET /* DEFAULT_CHARSET*/;
lf.lfPitchAndFamily = 0;
//EnumFontsA(dc, NULL, EnumFontCallback, NULL);
//EnumFontFamiliesA(dc, NULL, EnumFontFamCallback, 0);
EnumFontFamiliesExA(dc, &lf, EnumFontFamCallback, 0, 0);
ReleaseDC(NULL, dc);
}
#endif #endif
#elif defined(__macosx__) #elif defined(__macosx__)
// Récupération de la liste des fonts avec fontconfig // Récupération de la liste des fonts avec fontconfig
@ -547,6 +597,104 @@ byte *Render_text_TTF(const char *str, int font_number, int size, int antialias,
} }
#endif #endif
#if defined(WIN32)
byte *Render_text_Win32(const char *str, int font_number, int size, int antialias, int bold, int italic, int *width, int *height, T_Palette palette)
{
int str_len;
HGDIOBJ oldobj;
HGDIOBJ oldfont;
RECT rect;
BITMAPINFO *bi;
HDC dc;
HBITMAP bm;
SIZE s;
byte * pixels = NULL;
byte * new_brush = NULL;
int i;
HFONT font;
const char * font_name;
font_name = Font_name(font_number);
font = CreateFontA(size, 0, 0, 0 /* nOrientation */,
bold ? FW_BOLD : FW_REGULAR, italic, 0 /* underline */, 0 /*strikeout */,
ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS,
antialias ? ANTIALIASED_QUALITY : NONANTIALIASED_QUALITY /* DEFAULT_QUALITY*/,
DEFAULT_PITCH | FF_DONTCARE, font_name);
if (font == NULL)
return NULL;
dc = CreateCompatibleDC(NULL);
oldfont = SelectObject(dc, font);
str_len = (int)strlen(str);
if (!GetTextExtentPoint32A(dc, str, str_len, &s))
{
s.cx = 320;
s.cy = 32;
}
bi = (BITMAPINFO*)_alloca(sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * 256);
memset(bi, 0, sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * 256);
bi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
bi->bmiHeader.biWidth = (s.cx + 3) & ~3;
bi->bmiHeader.biHeight = -s.cy;
bi->bmiHeader.biPlanes = 1;
bi->bmiHeader.biBitCount = 8;
bi->bmiHeader.biCompression = BI_RGB;
for (i = 0; i < 255; i++) {
bi->bmiColors[i].rgbBlue = i;
bi->bmiColors[i].rgbBlue = i;
bi->bmiColors[i].rgbBlue = i;
}
bm = CreateDIBSection(dc, bi, DIB_RGB_COLORS, &pixels, NULL, 0);
oldobj = SelectObject(dc, bm);
SetTextColor(dc, RGB(255,255,255));
SetBkColor(dc, RGB(0,0,0));
//SetBkMode(dc,TRANSPARENT);
rect.left=0;
rect.top=0;
rect.right = s.cx;
rect.bottom = s.cy;
DrawTextA(dc, str, str_len, &rect, DT_LEFT | DT_SINGLELINE | DT_NOCLIP | DT_NOPREFIX ) ;
GdiFlush();
SelectObject(dc, oldobj);
SelectObject(dc, oldfont);
new_brush = malloc(s.cx*s.cy);
if (antialias)
{
int y;
// TODO complete the antialiasing processing
for (y = 0; y < s.cy; y++)
{
memcpy(new_brush + y * s.cx, pixels + y * bi->bmiHeader.biWidth, s.cx);
}
}
else
{
int x, y;
for (y = 0; y < s.cy; y++)
{
for (x = 0; x < s.cx; x++)
{
byte v = pixels[y*bi->bmiHeader.biWidth+x];
new_brush[y*s.cx+x] = (v != 0) ? Fore_color : Back_color;
}
}
memcpy(palette, Main.palette, sizeof(T_Palette));
}
*width = s.cx;
*height = s.cy;
DeleteObject(bm);
ReleaseDC(NULL, dc);
DeleteObject(font);
return new_brush;
}
#endif
#if defined(USE_SDL) || defined(USE_SDL2) #if defined(USE_SDL) || defined(USE_SDL2)
byte *Render_text_SFont(const char *str, int font_number, int *width, int *height, T_Palette palette) byte *Render_text_SFont(const char *str, int font_number, int *width, int *height, T_Palette palette)
{ {
@ -703,7 +851,9 @@ byte *Render_text(const char *str, int font_number, int size, int antialias, int
font = font->Next; font = font->Next;
if (font->Is_truetype) if (font->Is_truetype)
{ {
#ifndef NOTTF #if defined(WIN32)
return Render_text_Win32(str, font_number, size, antialias, bold, italic, width, height, palette);
#elif !defined(NOTTF)
return Render_text_TTF(str, font_number, size, antialias, bold, italic, width, height, palette); return Render_text_TTF(str, font_number, size, antialias, bold, italic, width, height, palette);
#else #else
return NULL; return NULL;