mirror of https://github.com/buggins/dlangui.git
fix freetype support
This commit is contained in:
parent
6bb605dde9
commit
5472b2456b
|
@ -146,9 +146,6 @@ struct Glyph
|
||||||
uint id;
|
uint id;
|
||||||
}
|
}
|
||||||
|
|
||||||
///< 8: character
|
|
||||||
//uint glyphIndex;
|
|
||||||
|
|
||||||
///< 4: width of glyph black box
|
///< 4: width of glyph black box
|
||||||
ubyte blackBoxX;
|
ubyte blackBoxX;
|
||||||
///< 5: height of glyph black box
|
///< 5: height of glyph black box
|
||||||
|
@ -158,9 +155,9 @@ struct Glyph
|
||||||
///< 7: Y origin for glyph
|
///< 7: Y origin for glyph
|
||||||
byte originY;
|
byte originY;
|
||||||
|
|
||||||
///< 10: full width of glyph
|
///< 8: full width of glyph
|
||||||
ubyte width;
|
ubyte width;
|
||||||
///< 11: usage flag, to handle cleanup of unused glyphs
|
///< 9: usage flag, to handle cleanup of unused glyphs
|
||||||
ubyte lastUsage;
|
ubyte lastUsage;
|
||||||
///< 12: glyph data, arbitrary size
|
///< 12: glyph data, arbitrary size
|
||||||
ubyte[] glyph;
|
ubyte[] glyph;
|
||||||
|
|
|
@ -57,13 +57,13 @@ version (USE_OPENGL) {
|
||||||
uint nextGlyphId() { return _nextGlyphId++; }
|
uint nextGlyphId() { return _nextGlyphId++; }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// glyph image cache
|
||||||
struct GlyphCache
|
struct GlyphCache
|
||||||
{
|
{
|
||||||
alias glyph_ptr = Glyph*;
|
alias glyph_ptr = Glyph*;
|
||||||
private glyph_ptr[][1024] _glyphs;
|
private glyph_ptr[][1024] _glyphs;
|
||||||
|
|
||||||
Glyph * find(uint ch) {
|
Glyph * find(dchar ch) {
|
||||||
ch = ch & 0xF_FFFF;
|
ch = ch & 0xF_FFFF;
|
||||||
//if (_array is null)
|
//if (_array is null)
|
||||||
// _array = new Glyph[0x10000];
|
// _array = new Glyph[0x10000];
|
||||||
|
@ -71,55 +71,70 @@ struct GlyphCache
|
||||||
glyph_ptr[] row = _glyphs[p];
|
glyph_ptr[] row = _glyphs[p];
|
||||||
if (row is null)
|
if (row is null)
|
||||||
return null;
|
return null;
|
||||||
ushort i = ch & 0xFF;
|
uint i = ch & 0xFF;
|
||||||
return row[i];
|
Glyph * res = row[i];
|
||||||
|
if (!res)
|
||||||
|
return null;
|
||||||
|
res.lastUsage = 1;
|
||||||
|
return res;
|
||||||
}
|
}
|
||||||
/// put glyph to cache
|
/// put glyph to cache
|
||||||
Glyph * put(uint ch, Glyph * glyph) {
|
Glyph * put(dchar ch, Glyph * glyph) {
|
||||||
|
ch = ch & 0xF_FFFF;
|
||||||
uint p = ch >> 8;
|
uint p = ch >> 8;
|
||||||
uint i = ch & 0xFF;
|
uint i = ch & 0xFF;
|
||||||
if (_glyphs[p] is null)
|
if (_glyphs[p] is null)
|
||||||
_glyphs[p] = new glyph_ptr[256];
|
_glyphs[p] = new glyph_ptr[256];
|
||||||
_glyphs[p][i] = glyph;
|
_glyphs[p][i] = glyph;
|
||||||
|
glyph.lastUsage = 1;
|
||||||
return glyph;
|
return glyph;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// removes entries not used after last call of checkpoint() or cleanup()
|
/// removes entries not used after last call of checkpoint() or cleanup()
|
||||||
void cleanup() {
|
void cleanup() {
|
||||||
// TODO
|
foreach(part; _glyphs) {
|
||||||
|
if (part !is null)
|
||||||
|
foreach(item; part) {
|
||||||
|
if (item && !item.lastUsage) {
|
||||||
|
version (USE_OPENGL) {
|
||||||
|
// notify about destroyed glyphs
|
||||||
|
if (_glyphDestroyCallback !is null) {
|
||||||
|
_glyphDestroyCallback(item.id);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
destroy(item);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// clear usage flags for all entries
|
// clear usage flags for all entries
|
||||||
void checkpoint() {
|
void checkpoint() {
|
||||||
|
foreach(part; _glyphs) {
|
||||||
|
if (part !is null)
|
||||||
|
foreach(item; part) {
|
||||||
|
if (item)
|
||||||
|
item.lastUsage = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// removes all entries
|
/// removes all entries
|
||||||
void clear() {
|
void clear() {
|
||||||
// notify about destroyed glyphs
|
foreach(part; _glyphs) {
|
||||||
version (USE_OPENGL) {
|
|
||||||
if (_glyphDestroyCallback !is null) {
|
|
||||||
foreach(part; _glyphs) {
|
|
||||||
if (part !is null)
|
|
||||||
foreach(item; part) {
|
|
||||||
if (item)
|
|
||||||
_glyphDestroyCallback(item.id);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/*
|
|
||||||
foreach(ref Glyph[] part; _glyphs) {
|
|
||||||
if (part !is null)
|
if (part !is null)
|
||||||
foreach(ref Glyph item; part) {
|
foreach(item; part) {
|
||||||
if (item.glyphIndex) {
|
if (item) {
|
||||||
item.glyphIndex = 0;
|
|
||||||
item.glyph = null;
|
|
||||||
version (USE_OPENGL) {
|
version (USE_OPENGL) {
|
||||||
item.id = 0;
|
// notify about destroyed glyphs
|
||||||
|
if (_glyphDestroyCallback !is null) {
|
||||||
|
_glyphDestroyCallback(item.id);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
destroy(item);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
*/
|
|
||||||
}
|
}
|
||||||
~this() {
|
~this() {
|
||||||
clear();
|
clear();
|
||||||
|
|
|
@ -341,17 +341,16 @@ class FreeTypeFont : Font {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
private Glyph tmpGlyphInfo;
|
|
||||||
override Glyph * getCharGlyph(dchar ch, bool withImage = true) {
|
override Glyph * getCharGlyph(dchar ch, bool withImage = true) {
|
||||||
if (ch > 0xFFFF) // do not support unicode chars above 0xFFFF - due to cache limitations
|
if (ch > 0xFFFF) // do not support unicode chars above 0xFFFF - due to cache limitations
|
||||||
return null;
|
return null;
|
||||||
long measureStart = std.datetime.Clock.currStdTime;
|
//long measureStart = std.datetime.Clock.currStdTime;
|
||||||
Glyph * found = _glyphCache.find(cast(ushort)ch);
|
Glyph * found = _glyphCache.find(cast(ushort)ch);
|
||||||
long measureEnd = std.datetime.Clock.currStdTime;
|
//long measureEnd = std.datetime.Clock.currStdTime;
|
||||||
long duration = measureEnd - measureStart;
|
//long duration = measureEnd - measureStart;
|
||||||
//if (duration > 10000)
|
//if (duration > 10000)
|
||||||
if (duration > 10000)
|
//if (duration > 10000)
|
||||||
Log.d("ft _glyphCache.find took ", duration / 10, " ns");
|
// Log.d("ft _glyphCache.find took ", duration / 10, " ns");
|
||||||
if (found !is null)
|
if (found !is null)
|
||||||
return found;
|
return found;
|
||||||
Log.v("Glyph ", ch, " is not found in cache, getting from font");
|
Log.v("Glyph ", ch, " is not found in cache, getting from font");
|
||||||
|
@ -361,11 +360,12 @@ class FreeTypeFont : Font {
|
||||||
if (!findGlyph(ch, '?', index, file))
|
if (!findGlyph(ch, '?', index, file))
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
if (!file.getGlyphInfo(ch, tmpGlyphInfo, 0, withImage))
|
Glyph * glyph = new Glyph;
|
||||||
|
if (!file.getGlyphInfo(ch, *glyph, 0, withImage))
|
||||||
return null;
|
return null;
|
||||||
if (withImage)
|
if (withImage)
|
||||||
return _glyphCache.put(cast(ushort)ch, &tmpGlyphInfo);
|
return _glyphCache.put(ch, glyph);
|
||||||
return &tmpGlyphInfo;
|
return glyph;
|
||||||
}
|
}
|
||||||
|
|
||||||
// draw text string to buffer
|
// draw text string to buffer
|
||||||
|
|
|
@ -659,7 +659,7 @@ int myWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int
|
||||||
Platform.setInstance(platform);
|
Platform.setInstance(platform);
|
||||||
|
|
||||||
|
|
||||||
if (false) {
|
if (true) {
|
||||||
/// testing freetype font manager
|
/// testing freetype font manager
|
||||||
import dlangui.graphics.ftfonts;
|
import dlangui.graphics.ftfonts;
|
||||||
import win32.shlobj;
|
import win32.shlobj;
|
||||||
|
|
Loading…
Reference in New Issue