Mercurial > mplayer.hg
comparison gui/skin/font.c @ 32734:cc58a1e919d9
Allow character in the font description file to be in UTF-8.
A character defined in the font description file can be either
an ASCII character, any character in the range of 0x80 to 0xFF
or - to avoid character set problems, and that is recommended -
a character in UTF-8 encoding now.
Non-ASCII characters will be stored in the nonASCIIidx array.
The indices 0..127 of this array correspond to the indices
128..255 of the Fnt array.
(This also settles the "Translate messages shown in the GUI window(s)
from UTF-8" issue.)
author | ib |
---|---|
date | Thu, 27 Jan 2011 18:04:19 +0000 |
parents | 6ff3cc81d602 |
children | 63844ef43932 |
comparison
equal
deleted
inserted
replaced
32733:e922613845cc | 32734:cc58a1e919d9 |
---|---|
44 if ( id == 25 ) return -2; | 44 if ( id == 25 ) return -2; |
45 | 45 |
46 if ( ( Fonts[id]=calloc( 1,sizeof( bmpFont ) ) ) == NULL ) return -1; | 46 if ( ( Fonts[id]=calloc( 1,sizeof( bmpFont ) ) ) == NULL ) return -1; |
47 | 47 |
48 av_strlcpy( Fonts[id]->name,name,128 ); // FIXME: as defined in font.h | 48 av_strlcpy( Fonts[id]->name,name,128 ); // FIXME: as defined in font.h |
49 for ( i=0;i<256;i++ ) | 49 for ( i=0;i<ASCII_CHRS+EXTRA_CHRS;i++ ) |
50 Fonts[id]->Fnt[i].x=Fonts[id]->Fnt[i].y=Fonts[id]->Fnt[i].sx=Fonts[id]->Fnt[i].sy=-1; | 50 Fonts[id]->Fnt[i].x=Fonts[id]->Fnt[i].y=Fonts[id]->Fnt[i].sx=Fonts[id]->Fnt[i].sy=-1; |
51 | 51 |
52 return id; | 52 return id; |
53 } | 53 } |
54 | 54 |
100 if ( command[0] == '"' ) | 100 if ( command[0] == '"' ) |
101 { | 101 { |
102 int i; | 102 int i; |
103 cutItem( command,command,'"',1 ); | 103 cutItem( command,command,'"',1 ); |
104 if ( !command[0] ) i=(int)'"'; | 104 if ( !command[0] ) i=(int)'"'; |
105 else if ( command[0] & 0x80 ) | |
106 { | |
107 for ( i = 0; i < EXTRA_CHRS; i++ ) | |
108 { | |
109 if ( !Fonts[id]->nonASCIIidx[i][0] ) | |
110 { | |
111 strncpy( Fonts[id]->nonASCIIidx[i], command, 4 ); | |
112 break; | |
113 } | |
114 } | |
115 if ( i == EXTRA_CHRS ) continue; | |
116 i += ASCII_CHRS; | |
117 } | |
105 else i=(int)command[0]; | 118 else i=(int)command[0]; |
106 cutItem( param,tmp,',',0 ); Fonts[id]->Fnt[i].x=atoi( tmp ); | 119 cutItem( param,tmp,',',0 ); Fonts[id]->Fnt[i].x=atoi( tmp ); |
107 cutItem( param,tmp,',',1 ); Fonts[id]->Fnt[i].y=atoi( tmp ); | 120 cutItem( param,tmp,',',1 ); Fonts[id]->Fnt[i].y=atoi( tmp ); |
108 cutItem( param,tmp,',',2 ); Fonts[id]->Fnt[i].sx=atoi( tmp ); | 121 cutItem( param,tmp,',',2 ); Fonts[id]->Fnt[i].sx=atoi( tmp ); |
109 cutItem( param,tmp,',',3 ); Fonts[id]->Fnt[i].sy=atoi( tmp ); | 122 cutItem( param,tmp,',',3 ); Fonts[id]->Fnt[i].sy=atoi( tmp ); |
135 if ( Fonts[i] ) | 148 if ( Fonts[i] ) |
136 if ( !strcmp( name,Fonts[i]->name ) ) return i; | 149 if ( !strcmp( name,Fonts[i]->name ) ) return i; |
137 return -1; | 150 return -1; |
138 } | 151 } |
139 | 152 |
153 // get Fnt index of character (utf8 or normal one) *str points to, | |
154 // then move pointer to next/previous character | |
155 int fntGetCharIndex( int id, unsigned char **str, gboolean utf8, int direction ) | |
156 { | |
157 unsigned char *p, uchar[4] = { 0, 0, 0, 0 }; | |
158 int i, c = -1; | |
159 | |
160 if ( **str & 0x80 ) | |
161 { | |
162 if ( utf8 ) | |
163 { | |
164 p = *str; | |
165 *str = g_utf8_next_char( *str ); | |
166 strncpy( uchar, p, *str - p ); | |
167 | |
168 if ( direction < 0 ) *str = g_utf8_prev_char( p ); | |
169 } | |
170 else | |
171 { | |
172 uchar[0] = **str; | |
173 *str += direction; | |
174 } | |
175 | |
176 for ( i = 0; ( i < EXTRA_CHRS ) && Fonts[id]->nonASCIIidx[i][0]; i++ ) | |
177 { | |
178 if ( strncmp( Fonts[id]->nonASCIIidx[i], uchar, 4 ) == 0 ) return i + ASCII_CHRS; | |
179 if ( !utf8 && ( Fonts[id]->nonASCIIidx[i][0] == (*uchar >> 6 | 0xc0) && Fonts[id]->nonASCIIidx[i][1] == (*uchar & 0x3f | 0x80) && Fonts[id]->nonASCIIidx[i][2] == 0 ) ) c = i + ASCII_CHRS; | |
180 } | |
181 } | |
182 else | |
183 { | |
184 c = **str; | |
185 | |
186 if ( utf8 && ( direction < 0 ) ) *str = g_utf8_prev_char( *str ); | |
187 else *str += direction; | |
188 } | |
189 | |
190 return c; | |
191 } | |
192 | |
140 int fntTextWidth( int id,char * str ) | 193 int fntTextWidth( int id,char * str ) |
141 { | 194 { |
142 int size = 0; | 195 int size = 0; |
143 int i; | 196 gboolean utf8; |
197 unsigned char *p; | |
144 | 198 |
145 if ( ( !Fonts[id] )||( !str[0] ) ) return 0; | 199 if ( ( !Fonts[id] )||( !str[0] ) ) return 0; |
146 | 200 |
147 for ( i=0;i < (int)strlen( str );i++ ) | 201 utf8 = g_utf8_validate( str, -1, NULL); |
148 { | 202 p = (unsigned char *) str; |
149 unsigned char c = (unsigned char)str[i]; | 203 |
150 if ( Fonts[id]->Fnt[c].sx == -1 ) c = ' '; | 204 while ( *p ) |
205 { | |
206 int c = fntGetCharIndex( id, &p, utf8, 1 ); | |
207 if ( c == -1 || Fonts[id]->Fnt[c].sx == -1 ) c = ' '; | |
151 size+= Fonts[id]->Fnt[ c ].sx; | 208 size+= Fonts[id]->Fnt[ c ].sx; |
152 } | 209 } |
153 return size; | 210 return size; |
154 } | 211 } |
155 | 212 |
156 int fntTextHeight( int id,char * str ) | 213 int fntTextHeight( int id,char * str ) |
157 { | 214 { |
158 int max = 0,i; | 215 int max = 0; |
216 gboolean utf8; | |
217 unsigned char *p; | |
159 | 218 |
160 if ( ( !Fonts[id] )||( !str[0] ) ) return 0; | 219 if ( ( !Fonts[id] )||( !str[0] ) ) return 0; |
161 | 220 |
162 for ( i=0;i < (int)strlen( str );i++ ) | 221 utf8 = g_utf8_validate( str, -1, NULL); |
222 p = (unsigned char *) str; | |
223 | |
224 while ( *p ) | |
163 { | 225 { |
164 int h; | 226 int h; |
165 unsigned char c = (unsigned char)str[i]; | 227 int c = fntGetCharIndex( id, &p, utf8, 1 ); |
166 if ( Fonts[id]->Fnt[c].sx == -1 ) c = ' '; | 228 if ( c == -1 || Fonts[id]->Fnt[c].sx == -1 ) c = ' '; |
167 h = Fonts[id]->Fnt[c].sy; | 229 h = Fonts[id]->Fnt[c].sy; |
168 if ( h > max ) max=h; | 230 if ( h > max ) max=h; |
169 } | 231 } |
170 return max; | 232 return max; |
171 } | 233 } |
172 | 234 |
173 txSample * fntRender( wItem * item,int px,const char * fmt,... ) | 235 txSample * fntRender( wItem * item,int px,const char * fmt,... ) |
174 { | 236 { |
175 va_list ap; | 237 va_list ap; |
176 unsigned char p[512]; | 238 unsigned char * u, p[512]; |
177 unsigned int c; | 239 int c, i, dx = 0, tw, fbw, iw, id, ofs; |
178 int i, dx = 0, tw, fbw, iw, id, ofs; | |
179 int x,y,fh,fw,fyc,yc; | 240 int x,y,fh,fw,fyc,yc; |
180 uint32_t * ibuf; | 241 uint32_t * ibuf; |
181 uint32_t * obuf; | 242 uint32_t * obuf; |
243 gboolean utf8; | |
182 | 244 |
183 va_start( ap,fmt ); | 245 va_start( ap,fmt ); |
184 vsnprintf( p,512,fmt,ap ); | 246 vsnprintf( p,512,fmt,ap ); |
185 va_end( ap ); | 247 va_end( ap ); |
186 | 248 |
222 | 284 |
223 } else dx+=px; | 285 } else dx+=px; |
224 | 286 |
225 ofs=dx; | 287 ofs=dx; |
226 | 288 |
227 for ( i=0;i < (int)strlen( p );i++ ) | 289 utf8 = g_utf8_validate( p, -1, NULL); |
228 { | 290 u = p; |
229 c=(unsigned int)p[i]; | 291 |
230 fw=Fonts[id]->Fnt[c].sx; | 292 while ( *u ) |
231 | 293 { |
232 if ( fw == -1 ) { c=32; fw=Fonts[id]->Fnt[c].sx; } | 294 c = fntGetCharIndex( id, &u, utf8, 1 ); |
295 | |
296 if ( c != -1 ) fw=Fonts[id]->Fnt[c].sx; | |
297 | |
298 if ( c == -1 || fw == -1 ) { c=32; fw=Fonts[id]->Fnt[c].sx; } | |
233 | 299 |
234 fh=Fonts[id]->Fnt[c].sy; | 300 fh=Fonts[id]->Fnt[c].sy; |
235 fyc=Fonts[id]->Fnt[c].y * fbw + Fonts[id]->Fnt[c].x; | 301 fyc=Fonts[id]->Fnt[c].y * fbw + Fonts[id]->Fnt[c].x; |
236 yc=dx; | 302 yc=dx; |
237 | 303 |
247 } | 313 } |
248 | 314 |
249 if ( ofs > 0 && tw > item->width ) | 315 if ( ofs > 0 && tw > item->width ) |
250 { | 316 { |
251 dx=ofs; | 317 dx=ofs; |
252 for ( i=(int)strlen( p );i > 0;i-- ) | 318 u = p + strlen( p ); |
253 { | 319 |
254 c=(unsigned int)p[i]; | 320 while ( u > p ) |
255 fw=Fonts[id]->Fnt[c].sx; | 321 { |
256 | 322 c = fntGetCharIndex( id, &u, utf8, -1 ); |
257 if ( fw == -1 ) { c=32; fw=Fonts[id]->Fnt[c].sx; } | 323 |
324 if ( c != -1) fw=Fonts[id]->Fnt[c].sx; | |
325 | |
326 if ( c == -1 || fw == -1 ) { c=32; fw=Fonts[id]->Fnt[c].sx; } | |
258 | 327 |
259 fh=Fonts[id]->Fnt[c].sy; | 328 fh=Fonts[id]->Fnt[c].sy; |
260 fyc=Fonts[id]->Fnt[c].y * fbw + Fonts[id]->Fnt[c].x; | 329 fyc=Fonts[id]->Fnt[c].y * fbw + Fonts[id]->Fnt[c].x; |
261 | 330 |
262 dx-=fw; yc=dx; | 331 dx-=fw; yc=dx; |