StreamFont.cpp
Go to the documentation of this file.
1 #include "StreamFont.hpp"
2 
4 
5 namespace iv
6 {
7 
9  Plain_StreamResourceSubprovider( inst, provider, "font" ),
10  cm( inst, this, "StreamFont_Subprovider" )
11 {
13 }
14 
16  StreamResource( inst, provider, path ),
17  Font( inst ),
18  cm( inst, this, "StreamFont" ),
19  access( inst )
20 {
21  this->cm.inherits( this->StreamResource::cm, this->Font::cm );
22  this->cm.owns( this->access.cm );
23 
25  [&]( std::istream & in )
26  {
27  this->Load( in );
28  }
29  );
30 }
31 
32 void StreamFont::ReadAdvance( Lex & lex )
33 {
34  lex.AcceptOperator( "{" );
35 
36  while( !lex.Failed() && !lex.IsNextOperator( "}" ) )
37  {
38  lex.AcceptKeyword( "glyph" );
39  uint32_t code = lex.AcceptInteger();
40  float advance = lex.AcceptDouble();
41  float width = lex.AcceptDouble();
42  if( !lex.Failed() )
43  {
44  this->_info.advances[ code ] = advance;
45  this->_info.widths[ code ] = width;
46  }
47  }
48 
49  lex.RecoverOperator( "}" );
50  lex.AcceptOperator( "}" );
51 }
52 
53 Font::Variant StreamFont::ReadVariant( Lex & lex )
54 {
55  lex.AcceptOperator( "{" );
56 
57  Font::Variant variant;
58  while( !lex.Failed() && !lex.IsNextOperator( "}" ) )
59  {
60  if( lex.IsNextKeyword( "texture" ) )
61  {
62  lex.AcceptKeyword( "texture" );
63  std::string filename = lex.AcceptString();
64  if( !lex.Failed() )
65  variant.texture = this->access.get< Texture >( this->resource_path().get_directory() / filename );
66  }
67  else
68  {
69  Glyph glyph;
70 
71  lex.AcceptKeyword( "glyph" );
72  glyph.code = lex.AcceptInteger();
73  glyph.pos_x = lex.AcceptInteger();
74  glyph.pos_y = lex.AcceptInteger();
75  glyph.width = lex.AcceptInteger();
76  glyph.height = lex.AcceptInteger();
77  glyph.bearing_x = lex.AcceptDouble();
78  glyph.bearing_y = lex.AcceptDouble();
79 
80  variant.glyphs[ glyph.code ] = glyph;
81  }
82  }
83 
84  lex.RecoverOperator( "}" );
85  lex.AcceptOperator( "}" );
86 
87  return variant;
88 }
89 
90 void StreamFont::Load( std::istream & in )
91 {
92  Lex lex( this->instance() );
93  lex.DefineKeyword( "line_height" );
94  lex.DefineKeyword( "ascender" );
95  lex.DefineKeyword( "descender" );
96  lex.DefineKeyword( "max_advance" );
97  lex.DefineKeyword( "advance" );
98  lex.DefineKeyword( "glyph" );
99  lex.DefineKeyword( "variant" );
100  lex.DefineKeyword( "msdf" );
101  lex.DefineKeyword( "fixed" );
102  lex.DefineKeyword( "texture" );
103  lex.DefineOperator( "{" );
104  lex.DefineOperator( "}" );
105 
106  Lex_LogTrace _trace( lex );
107 
108  lex.Init( in );
109 
110  while( !lex.Failed() && !lex.IsNext( Lex::Eof ) )
111  {
112  if( lex.IsNextKeyword( "line_height" ) )
113  {
114  lex.AcceptKeyword( "line_height" );
115  this->_info.line_height = lex.AcceptDouble();
116  }
117  else if( lex.IsNextKeyword( "ascender" ) )
118  {
119  lex.AcceptKeyword( "ascender" );
120  this->_info.ascender = lex.AcceptDouble();
121  }
122  else if( lex.IsNextKeyword( "descender" ) )
123  {
124  lex.AcceptKeyword( "descender" );
125  this->_info.descender = lex.AcceptDouble();
126  }
127  else if( lex.IsNextKeyword( "max_advance" ) )
128  {
129  lex.AcceptKeyword( "max_advance" );
130  this->_info.max_advance = lex.AcceptDouble();
131  }
132  else if( lex.IsNextKeyword( "advance" ) )
133  {
134  lex.AcceptKeyword( "advance" );
135  this->ReadAdvance( lex );
136  }
137  else
138  {
139  lex.AcceptKeyword( "variant" );
140  if( lex.IsNextKeyword( "msdf" ) )
141  {
142  lex.AcceptKeyword( "msdf" );
143  int size = lex.AcceptInteger();
144  Variant variant = this->ReadVariant( lex );
145 
146  if( !lex.Failed() )
147  {
148  variant.size = size;
149  this->_variant_msdf = variant;
150  }
151  }
152  else
153  {
154  lex.AcceptKeyword( "fixed" );
155  int size = lex.AcceptInteger();
156  Variant variant = this->ReadVariant( lex );
157 
158  if( !lex.Failed() )
159  {
160  variant.size = size;
161  this->_variant_fixed[ size ] = variant;
162  }
163  }
164  }
165  }
166 }
167 
168 }