33
33
static OpenThreads::ReentrantMutex s_FontFileMutex;
35
Font::FontMutex* osgText::Font::getSerializeFontCallsMutex()
37
static OpenThreads::Mutex s_FontCallsMutex;
38
return &s_FontCallsMutex;
41
35
std::string osgText::findFontFile(const std::string& str)
43
37
// try looking in OSGFILEPATH etc first for fonts.
148
osg::ref_ptr<Font> osgText::readRefFontFile(const std::string& filename, const osgDB::ReaderWriter::Options* userOptions)
150
if (filename=="") return 0;
152
std::string foundFile = findFontFile(filename);
153
if (foundFile.empty()) return 0;
155
OpenThreads::ScopedLock<OpenThreads::Mutex> lock(s_FontFileMutex);
157
osg::ref_ptr<osgDB::ReaderWriter::Options> localOptions;
160
localOptions = new osgDB::ReaderWriter::Options;
161
localOptions->setObjectCacheHint(osgDB::ReaderWriter::Options::CACHE_OBJECTS);
164
osg::ref_ptr<osg::Object> object = osgDB::readRefObjectFile(foundFile, userOptions ? userOptions : localOptions.get());
166
// if the object is a font then return it.
167
osgText::Font* font = dynamic_cast<osgText::Font*>(object.get());
168
if (font) return osg::ref_ptr<Font>(font);
173
osg::ref_ptr<Font> osgText::readRefFontStream(std::istream& stream, const osgDB::ReaderWriter::Options* userOptions)
175
OpenThreads::ScopedLock<OpenThreads::Mutex> lock(s_FontFileMutex);
177
osg::ref_ptr<osgDB::ReaderWriter::Options> localOptions;
180
localOptions = new osgDB::ReaderWriter::Options;
181
localOptions->setObjectCacheHint(osgDB::ReaderWriter::Options::CACHE_OBJECTS);
184
// there should be a better way to get the FreeType ReaderWriter by name...
185
osgDB::ReaderWriter *reader = osgDB::Registry::instance()->getReaderWriterForExtension("ttf");
186
if (reader == 0) return 0;
187
osgDB::ReaderWriter::ReadResult rr = reader->readObject(stream, userOptions ? userOptions : localOptions.get());
190
osg::notify(osg::WARN) << rr.message() << std::endl;
193
if (!rr.validObject()) return 0;
195
// if the object is a font then return it.
196
osgText::Font* font = dynamic_cast<osgText::Font*>(rr.getObject());
197
if (font) return osg::ref_ptr<Font>(font);
155
202
Font::Font(FontImplementation* implementation):
156
203
osg::Object(true),
160
205
_marginRatio(0.02),
161
206
_textureWidthHint(1024),
211
void Font::setFontResolution(unsigned int width, unsigned int height)
213
if (_implementation.valid()) _implementation->setFontResolution(width, height);
216
unsigned int Font::getFontWidth() const
221
unsigned int Font::getFontHeight() const
226
256
void Font::setGlyphImageMargin(unsigned int margin)
228
258
_margin = margin;
295
Font::Glyph* Font::getGlyph(unsigned int charcode)
325
Font::Glyph* Font::getGlyph(const FontResolution& fontRes, unsigned int charcode)
297
SizeGlyphMap::iterator itr = _sizeGlyphMap.find(SizePair(_width,_height));
298
if (itr!=_sizeGlyphMap.end())
300
GlyphMap& glyphmap = itr->second;
301
GlyphMap::iterator gitr = glyphmap.find(charcode);
302
if (gitr!=glyphmap.end()) return gitr->second.get();
328
OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_glyphMapMutex);
329
FontSizeGlyphMap::iterator itr = _sizeGlyphMap.find(fontRes);
330
if (itr!=_sizeGlyphMap.end())
332
GlyphMap& glyphmap = itr->second;
333
GlyphMap::iterator gitr = glyphmap.find(charcode);
334
if (gitr!=glyphmap.end()) return gitr->second.get();
305
if (_implementation.valid()) return _implementation->getGlyph(charcode);
338
if (_implementation.valid()) return _implementation->getGlyph(fontRes, charcode);
348
381
// const_cast<Font*>(this)->_sizeGlyphMap.clear();
351
osg::Vec2 Font::getKerning(unsigned int leftcharcode,unsigned int rightcharcode, KerningType kerningType)
384
osg::Vec2 Font::getKerning(const FontResolution& fontRes, unsigned int leftcharcode,unsigned int rightcharcode, KerningType kerningType)
353
if (_implementation.valid()) return _implementation->getKerning(leftcharcode,rightcharcode,kerningType);
386
if (_implementation.valid()) return _implementation->getKerning(fontRes, leftcharcode,rightcharcode,kerningType);
354
387
else return osg::Vec2(0.0f,0.0f);
365
void Font::addGlyph(unsigned int width, unsigned int height, unsigned int charcode, Glyph* glyph)
398
void Font::addGlyph(const FontResolution& fontRes, unsigned int charcode, Glyph* glyph)
367
_sizeGlyphMap[SizePair(width,height)][charcode]=glyph;
400
OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_glyphMapMutex);
402
_sizeGlyphMap[fontRes][charcode]=glyph;
369
404
int posX=0,posY=0;
631
666
if (s_renderer &&
632
667
(strstr((const char*)s_renderer,"Radeon")!=0) ||
633
(strstr((const char*)s_renderer,"RADEON")!=0))
668
(strstr((const char*)s_renderer,"RADEON")!=0) ||
669
(strstr((const char*)s_renderer,"ALL-IN-WONDER")!=0))
635
671
// we're running on an ATI, so need to work around its
636
672
// subloading bugs by loading all at once.
637
673
s_subloadAllGlyphsTogether = true;
676
if (s_renderer && strstr((const char*)s_renderer,"Sun")!=0)
678
// we're running on an solaris x server, so need to work around its
679
// subloading bugs by loading all at once.
680
s_subloadAllGlyphsTogether = true;
640
683
const char* str = getenv("OSG_TEXT_INCREMENTAL_SUBLOADING");
643
s_subloadAllGlyphsTogether = strcmp(str,"OFF")==0 || strcmp(str,"Off")==0 || strcmp(str,"Off")==0;
686
s_subloadAllGlyphsTogether = strcmp(str,"OFF")==0 || strcmp(str,"Off")==0 || strcmp(str,"off")==0;
761
804
// all the methods in Font::Glyph have been made non inline because VisualStudio6.0 is STUPID, STUPID, STUPID PILE OF JUNK.
762
Font::Glyph::Glyph() {}
763
Font::Glyph::~Glyph() {}
805
Font::Glyph::Glyph():
808
_horizontalBearing(0.0f,0.f),
809
_horizontalAdvance(0.f),
810
_verticalBearing(0.0f,0.f),
811
_verticalAdvance(0.f),
815
_minTexCoord(0.0f,0.0f),
816
_maxTexCoord(0.0f,0.0f)
818
setThreadSafeRefUnref(true);
821
Font::Glyph::~Glyph()
765
825
unsigned int Font::Glyph::getGlyphCode() const { return _glyphCode; }
801
861
osg::notify(osg::WARN)<<"before Font::Glyph::subload(): detected OpenGL error '"<<gluErrorString(errorNo)<<std::endl;
864
if(s() <= 0 || t() <= 0)
866
osg::notify(osg::INFO)<<"Font::Glyph::subload(): texture sub-image width and/or height of 0, ignoring operation."<<std::endl;
804
870
glPixelStorei(GL_UNPACK_ALIGNMENT,getPacking());
806
872
glTexSubImage2D(GL_TEXTURE_2D,0,