SuperTuxKart
font_with_face.hpp
1 //
2 // SuperTuxKart - a fun racing game with go-kart
3 // Copyright (C) 2016 SuperTuxKart-Team
4 //
5 // This program is free software; you can redistribute it and/or
6 // modify it under the terms of the GNU General Public License
7 // as published by the Free Software Foundation; either version 3
8 // of the License, or (at your option) any later version.
9 //
10 // This program is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 // GNU General Public License for more details.
14 //
15 // You should have received a copy of the GNU General Public License
16 // along with this program; if not, write to the Free Software
17 // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18 
19 #ifndef HEADER_FONT_WITH_FACE_HPP
20 #define HEADER_FONT_WITH_FACE_HPP
21 
22 #include "utils/cpp2011.hpp"
23 #include "utils/leak_check.hpp"
24 #include "utils/no_copy.hpp"
25 
26 #include <algorithm>
27 #include <cassert>
28 #include <map>
29 #include <set>
30 #include <string>
31 
32 #ifndef SERVER_ONLY
33 #include <ft2build.h>
34 #include FT_FREETYPE_H
35 #include FT_OUTLINE_H
36 #endif
37 
38 #include <irrlicht.h>
39 
40 using namespace irr;
41 
42 const int BEARING = 64;
43 
44 class FaceTTF;
45 class FontSettings;
46 struct FontArea;
47 
55 class FontWithFace : public NoCopy
56 {
57 public:
61  {
62  public:
68  virtual void collectChar(video::ITexture* texture,
69  const core::rect<float>& destRect,
70  const core::rect<s32>& sourceRect,
71  const video::SColor* const colors) = 0;
72  };
73 
74 protected:
77 
80 
81  // ------------------------------------------------------------------------
87  void insertCharacters(const wchar_t* in_ptr, bool first_load = false)
88  {
89  if (!supportLazyLoadChar() && !first_load) return;
90 
91  for (const wchar_t* p = in_ptr; *p; ++p)
92  {
93  if (*p == L'\r' || *p == L'\n' || *p < (wchar_t)32)
94  continue;
95  if (!loadedChar(*p))
96  {
97  loadGlyphInfo(*p);
98  if (supportChar(*p))
99  addLazyLoadChar(*p);
100  else if (m_fallback_font != NULL)
101  {
102  if (!m_fallback_font->loadedChar(*p))
103  {
104  m_fallback_font->loadGlyphInfo(*p);
105  if (m_fallback_font->supportChar(*p))
106  m_fallback_font->addLazyLoadChar(*p);
107  }
108  }
109  }
110  }
111  }
112  // ------------------------------------------------------------------------
113  void updateCharactersList();
114  // ------------------------------------------------------------------------
118  void setFallbackFont(FontWithFace* face) { m_fallback_font = face; }
119  // ------------------------------------------------------------------------
122  void setFallbackFontScale(float scale) { m_fallback_font_scale = scale; }
123 
124 private:
126  struct GlyphInfo
127  {
128  GlyphInfo(unsigned int font_num = 0, unsigned int glyph_idx = 0) :
129  font_number(font_num), glyph_index(glyph_idx) {}
131  unsigned int font_number;
133  unsigned int glyph_index;
134  };
135 
138 
141 
144 
146  std::set<wchar_t> m_new_char_holder;
147 
149  gui::IGUISpriteBank* m_spritebank;
150 
152  unsigned int m_current_height;
153 
155  unsigned int m_used_width;
156 
158  unsigned int m_used_height;
159 
161  unsigned int m_face_dpi;
162 
167  std::map<wchar_t, GlyphInfo> m_character_glyph_info_map;
168 
169  // ------------------------------------------------------------------------
170  float getCharWidth(const FontArea& area, bool fallback, float scale) const;
171  // ------------------------------------------------------------------------
175  bool loadedChar(wchar_t c) const
176  {
177  std::map<wchar_t, GlyphInfo>::const_iterator n =
178  m_character_glyph_info_map.find(c);
179  if (n != m_character_glyph_info_map.end())
180  return true;
181  return false;
182  }
183  // ------------------------------------------------------------------------
188  const GlyphInfo& getGlyphInfo(wchar_t c) const
189  {
190  std::map<wchar_t, GlyphInfo>::const_iterator n =
191  m_character_glyph_info_map.find(c);
192  // Make sure we always find GlyphInfo
193  assert(n != m_character_glyph_info_map.end());
194  return n->second;
195  }
196  // ------------------------------------------------------------------------
201  bool supportChar(wchar_t c)
202  {
203  std::map<wchar_t, GlyphInfo>::const_iterator n =
204  m_character_glyph_info_map.find(c);
205  if (n != m_character_glyph_info_map.end())
206  {
207  return n->second.glyph_index > 0;
208  }
209  return false;
210  }
211  // ------------------------------------------------------------------------
212  void loadGlyphInfo(wchar_t c);
213  // ------------------------------------------------------------------------
214  void createNewGlyphPage();
215  // ------------------------------------------------------------------------
217  void addLazyLoadChar(wchar_t c) { m_new_char_holder.insert(c); }
218  // ------------------------------------------------------------------------
220  virtual bool supportLazyLoadChar() const { return true; }
221  // ------------------------------------------------------------------------
224  virtual unsigned int getGlyphPageSize() const = 0;
225  // ------------------------------------------------------------------------
227  virtual float getScalingFactorOne() const = 0;
228  // ------------------------------------------------------------------------
230  virtual unsigned int getScalingFactorTwo() const = 0;
231  // ------------------------------------------------------------------------
233  virtual bool isBold() const { return false; }
234  // ------------------------------------------------------------------------
235  const FontArea* getUnknownFontArea() const;
236  // ------------------------------------------------------------------------
237  std::vector<gui::GlyphLayout> text2GlyphsWithoutShaping(
238  const core::stringw& t);
239  // ------------------------------------------------------------------------
240 #ifndef SERVER_ONLY
241 
244  virtual int shapeOutline(FT_Outline* outline) const { return 0; }
245 #endif
246 
247 public:
248  LEAK_CHECK()
249  // ------------------------------------------------------------------------
250  FontWithFace(const std::string& name);
251  // ------------------------------------------------------------------------
252  virtual ~FontWithFace();
253  // ------------------------------------------------------------------------
254  virtual void init();
255  // ------------------------------------------------------------------------
256  virtual void reset();
257  // ------------------------------------------------------------------------
258  virtual core::dimension2d<u32> getDimension(const core::stringw& text,
259  FontSettings* font_settings = NULL);
260  // ------------------------------------------------------------------------
261  int getCharacterFromPos(const wchar_t* text, int pixel_x,
262  FontSettings* font_settings = NULL) const;
263  // ------------------------------------------------------------------------
264  void render(const std::vector<gui::GlyphLayout>& gl,
265  const core::rect<s32>& position, const video::SColor& color,
266  bool hcenter, bool vcenter, const core::rect<s32>* clip,
267  FontSettings* font_settings,
268  FontCharCollector* char_collector = NULL);
269  // ------------------------------------------------------------------------
270  virtual void drawText(const core::stringw& text,
271  const core::rect<s32>& position,
272  const video::SColor& color, bool hcenter,
273  bool vcenter, const core::rect<s32>* clip,
274  FontSettings* font_settings,
275  FontCharCollector* char_collector = NULL);
276  // ------------------------------------------------------------------------
277  void drawTextQuick(const core::stringw& text,
278  const core::rect<s32>& position,
279  const video::SColor& color, bool hcenter, bool vcenter,
280  const core::rect<s32>* clip,
281  FontSettings* font_settings,
282  FontCharCollector* char_collector = NULL);
283  // ------------------------------------------------------------------------
284  void dumpGlyphPage(const std::string& name);
285  // ------------------------------------------------------------------------
286  void dumpGlyphPage();
287  // ------------------------------------------------------------------------
289  gui::IGUISpriteBank* getSpriteBank() const { return m_spritebank; }
290  // ------------------------------------------------------------------------
291  const FontArea& getAreaFromCharacter(const wchar_t c,
292  bool* fallback_font) const;
293  // ------------------------------------------------------------------------
295  unsigned int getDPI() const { return m_face_dpi; }
296  // ------------------------------------------------------------------------
297  FaceTTF* getFaceTTF() const { return m_face_ttf; }
298  // ------------------------------------------------------------------------
299  void insertGlyph(unsigned font_number, unsigned glyph_index);
300  // ------------------------------------------------------------------------
301  int getFontMaxHeight() const { return m_font_max_height; }
302  // ------------------------------------------------------------------------
303  int getGlyphMaxHeight() const { return m_glyph_max_height; }
304  // ------------------------------------------------------------------------
305  virtual bool disableTextShaping() const { return false; }
306  // ------------------------------------------------------------------------
307  float getInverseShaping() const { return m_inverse_shaping; }
308  // ------------------------------------------------------------------------
309  virtual bool useColorGlyphPage() const { return false; }
310  // ------------------------------------------------------------------------
311  void setDPI();
312 }; // FontWithFace
313 
314 #endif
315 /* EOF */
const GlyphInfo & getGlyphInfo(wchar_t c) const
Get the GlyphInfo from m_character_glyph_info_map about a character.
Definition: font_with_face.hpp:188
float m_fallback_font_scale
Scaling for fallback font.
Definition: font_with_face.hpp:143
This class will load a list of TTF files from FontManager, and save them inside m_ft_faces for FontWi...
Definition: face_ttf.hpp:56
gui::IGUISpriteBank * m_spritebank
Sprite bank to store each glyph.
Definition: font_with_face.hpp:149
gui::IGUISpriteBank * getSpriteBank() const
Return the sprite bank.
Definition: font_with_face.hpp:289
A class for STKTextBillboard to get font info to render billboard text.
Definition: font_with_face.hpp:60
bool supportChar(wchar_t c)
Tells whether a character is supported by all TTFs in m_face_ttf which is determined by GlyphInfo of ...
Definition: font_with_face.hpp:201
void setFallbackFont(FontWithFace *face)
Set the fallback font for this font, so if some character is missing in this font, it will use that fallback font to try rendering it.
Definition: font_with_face.hpp:118
unsigned int m_used_height
The used height in glyph page.
Definition: font_with_face.hpp:158
unsigned int m_face_dpi
The dpi of this font.
Definition: font_with_face.hpp:161
Definition: three_d_animation.hpp:32
unsigned int m_used_width
The used width in glyph page.
Definition: font_with_face.hpp:155
float m_inverse_shaping
Used to undo the scale on text shaping, only need to take care of width.
Definition: font_with_face.hpp:165
std::map< wchar_t, GlyphInfo > m_character_glyph_info_map
Store a list of loaded and tested character to a GlyphInfo.
Definition: font_with_face.hpp:167
virtual bool isBold() const
Override it if sub-class has bold outline.
Definition: font_with_face.hpp:233
bool loadedChar(wchar_t c) const
Test if a character has already been tried to be loaded.
Definition: font_with_face.hpp:175
int m_glyph_max_height
Used in top side bearing calculation.
Definition: font_with_face.hpp:79
An abstract class which contains functions which convert vector fonts into bitmap and render them in ...
Definition: font_with_face.hpp:55
Mapping of glyph index to a TTF in FaceTTF.
Definition: font_with_face.hpp:126
int m_font_max_height
Used in vertical dimension calculation.
Definition: font_with_face.hpp:76
Glyph metrics for each glyph loaded.
Definition: face_ttf.hpp:36
This class stores settings when rendering fonts, used when instantiating irr::gui::ScalableFont.
Definition: font_settings.hpp:32
FaceTTF * m_face_ttf
FaceTTF to load glyph from.
Definition: font_with_face.hpp:137
Utility class, you can inherit from this class to disallow the assignment operator and copy construct...
Definition: no_copy.hpp:25
unsigned int font_number
Index to a TTF in FaceTTF.
Definition: font_with_face.hpp:131
unsigned int getDPI() const
Return the dpi of this face.
Definition: font_with_face.hpp:295
unsigned int glyph_index
Glyph index in the TTF, 0 means no such glyph.
Definition: font_with_face.hpp:133
std::set< wchar_t > m_new_char_holder
A temporary holder to store new characters to be inserted.
Definition: font_with_face.hpp:146
void insertCharacters(const wchar_t *in_ptr, bool first_load=false)
Check characters to see if they are loaded in font, if not load them.
Definition: font_with_face.hpp:87
void addLazyLoadChar(wchar_t c)
Add a character into m_new_char_holder for lazy loading later.
Definition: font_with_face.hpp:217
virtual int shapeOutline(FT_Outline *outline) const
Override it if any outline shaping is needed to be done before rendering the glyph into bitmap...
Definition: font_with_face.hpp:244
void setFallbackFontScale(float scale)
Set the scaling of fallback font.
Definition: font_with_face.hpp:122
unsigned int m_current_height
The current max height at current drawing line in glyph page.
Definition: font_with_face.hpp:152
FontWithFace * m_fallback_font
Fallback font to use if some character isn&#39;t supported by this font.
Definition: font_with_face.hpp:140
virtual bool supportLazyLoadChar() const
Override it if sub-class should not do lazy loading characters.
Definition: font_with_face.hpp:220