rubysdl 2.1.2 → 2.1.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (78) hide show
  1. data/NEWS.en +8 -0
  2. data/NEWS.ja +8 -0
  3. data/README.en +22 -15
  4. data/README.ja +31 -20
  5. data/depend +2 -0
  6. data/doc-en/event.rsd +3 -0
  7. data/doc-en/time.rsd +1 -1
  8. data/doc-en/video.rsd +8 -8
  9. data/doc.txt +32 -0
  10. data/doc/event.rsd +5 -0
  11. data/doc/opengl.rsd +160 -0
  12. data/doc/rsd.rb +4 -3
  13. data/doc/time.rsd +1 -1
  14. data/doc/video.rsd +8 -8
  15. data/extconf.rb +30 -15
  16. data/lib/sdl.rb +2 -1
  17. data/lib/sdl1_compatible.rb +20 -0
  18. data/mkpkg.sh +28 -0
  19. data/rubysdl.gemspec +21 -0
  20. data/rubysdl.h +1 -0
  21. data/rubysdl_cdrom.c +0 -10
  22. data/rubysdl_event.c +30 -11
  23. data/rubysdl_event_key.c +0 -5
  24. data/rubysdl_image.c +2 -2
  25. data/rubysdl_joystick.c +0 -18
  26. data/rubysdl_kanji.c +0 -5
  27. data/rubysdl_main.c +0 -2
  28. data/rubysdl_mixer.c +2 -18
  29. data/rubysdl_mouse.c +0 -4
  30. data/rubysdl_rwops.c +4 -0
  31. data/rubysdl_sdlskk.c +0 -3
  32. data/rubysdl_sge_video.c +0 -14
  33. data/rubysdl_smpeg.c +0 -1
  34. data/rubysdl_time.c +0 -10
  35. data/rubysdl_ttf.c +0 -3
  36. data/rubysdl_video.c +2 -30
  37. data/rubysdl_wm.c +0 -5
  38. data/sample/caption.rb +21 -0
  39. data/sge/INSTALL +72 -0
  40. data/sge/LICENSE +504 -0
  41. data/sge/Makefile +83 -0
  42. data/sge/Makefile.conf +63 -0
  43. data/sge/README +219 -0
  44. data/sge/Todo +7 -0
  45. data/sge/WhatsNew +224 -0
  46. data/sge/sge.h +31 -0
  47. data/sge/sge_blib.cpp +1939 -0
  48. data/sge/sge_blib.h +68 -0
  49. data/sge/sge_bm_text.cpp +451 -0
  50. data/sge/sge_bm_text.h +71 -0
  51. data/sge/sge_collision.cpp +388 -0
  52. data/sge/sge_collision.h +54 -0
  53. data/sge/sge_config.h +6 -0
  54. data/sge/sge_internal.h +152 -0
  55. data/sge/sge_misc.cpp +92 -0
  56. data/sge/sge_misc.h +37 -0
  57. data/sge/sge_primitives.cpp +2516 -0
  58. data/sge/sge_primitives.h +111 -0
  59. data/sge/sge_rotation.cpp +683 -0
  60. data/sge/sge_rotation.h +46 -0
  61. data/sge/sge_shape.cpp +762 -0
  62. data/sge/sge_shape.h +365 -0
  63. data/sge/sge_surface.cpp +1090 -0
  64. data/sge/sge_surface.h +100 -0
  65. data/sge/sge_textpp.cpp +785 -0
  66. data/sge/sge_textpp.h +270 -0
  67. data/sge/sge_tt_text.cpp +1456 -0
  68. data/sge/sge_tt_text.h +114 -0
  69. data/utils/buildtest.sh +29 -0
  70. data/win32/README.en.win32 +72 -0
  71. data/win32/README.ja.win32 +80 -0
  72. data/win32/install_rubysdl.rb +30 -0
  73. data/win32/mkpkg.sh +72 -0
  74. metadata +136 -113
  75. data/rubysdl_ref.en.html +0 -5879
  76. data/rubysdl_ref.en.rd +0 -6601
  77. data/rubysdl_ref.html +0 -6194
  78. data/rubysdl_ref.rd +0 -6950
@@ -0,0 +1,270 @@
1
+ /*
2
+ * SDL Graphics Extension
3
+ * Text/TrueType classes (header)
4
+ *
5
+ * Started 990826 / 010207 (new version)
6
+ *
7
+ * License: LGPL v2+ (see the file LICENSE)
8
+ * (c)1999-2003 Anders Lindstr�m
9
+ *
10
+ * Uses the excellent FreeType 2 library, available at:
11
+ * http://www.freetype.org/
12
+ */
13
+
14
+ /*********************************************************************
15
+ * This library is free software; you can redistribute it and/or *
16
+ * modify it under the terms of the GNU Library General Public *
17
+ * License as published by the Free Software Foundation; either *
18
+ * version 2 of the License, or (at your option) any later version. *
19
+ *********************************************************************/
20
+
21
+ #ifndef sge_textpp_H
22
+ #define sge_textpp_H
23
+
24
+ #include "SDL.h"
25
+ #include "sge_internal.h"
26
+
27
+ #ifndef _SGE_NO_CLASSES
28
+
29
+ #include <string>
30
+ #include <stdio.h>
31
+ #include "sge_tt_text.h"
32
+ #include "sge_bm_text.h"
33
+ #include "sge_shape.h"
34
+
35
+ //==================================================================================
36
+ // Edits text from SDL_Event
37
+ //==================================================================================
38
+ class DECLSPEC sge_TextEditor
39
+ {
40
+ protected:
41
+ //The text is stored in a double linked list
42
+
43
+ //The elements in the linked list
44
+ struct node{
45
+ Uint16 c; //Unicode char
46
+
47
+ node* next;
48
+ node* prev;
49
+ };
50
+
51
+ //List metadata
52
+ node* start;
53
+ node* end;
54
+ node* cursor; //The current node (the cursor)
55
+
56
+ Uint16 cursor_char; //The charactar for the cursor
57
+ unsigned int chars; //Size of the string (without the cursor)
58
+ unsigned int mChars; //Max chars, 0 is default (unlimited)
59
+
60
+ //Create and fill a new node
61
+ node* new_node(node* p, node* n, Uint16 c);
62
+
63
+ //Swap two nodes
64
+ bool nswap(node* one, node* two);
65
+
66
+ //This indicates that the text has changed since last
67
+ //set to false (used for derived classes)
68
+ bool text_changed;
69
+ public:
70
+ //Creator
71
+ sge_TextEditor(void);
72
+ //Destructor
73
+ virtual ~sge_TextEditor(void);
74
+
75
+ //Adds an char before the cursor
76
+ bool insert(Uint16 c);
77
+ //Removes the char left of cursor
78
+ bool remove_left(void);
79
+ //Removes the char right of cursor
80
+ bool remove_right(void);
81
+
82
+ //Move cursor left
83
+ inline bool move_left(void);
84
+ //Move cursor right
85
+ inline bool move_right(void);
86
+ //Move cursor to the start
87
+ bool move_start(void);
88
+ //Move cursor to the end
89
+ bool move_end(void);
90
+
91
+ //Returns text as latin1 or unicode with or without the cursor char
92
+ std::string get_string(bool wCursor=true);
93
+ //std::basic_string<Uint16> get_ustring(bool wCursor=true);
94
+ //Returns a unicode c-style string (allocated with new)
95
+ Uint16* get_ucstring(bool wCursor=true);
96
+
97
+ //Process a SDL_Event
98
+ //Returns true if the text changed
99
+ virtual bool check(SDL_Event* event);
100
+
101
+ //Change the cursor char
102
+ void change_cursor(Uint16 c){cursor_char=c; cursor->c=c;}
103
+
104
+ //Change the text
105
+ void clear_text(void);
106
+ void change_text(const std::string s);
107
+ //void change_utext(const std::basic_string<Uint16> s);
108
+ void change_uctext(Uint16 *text);
109
+ void change_textf(const char *text, ...); //printf c-style... urk
110
+
111
+ //Set max chars (default: limited only by memory)
112
+ void max_chars(unsigned int c){mChars=c;}
113
+
114
+ //Returns the number of characters in the current string
115
+ unsigned int get_chars(void){return chars;}
116
+ };
117
+
118
+
119
+
120
+ //==================================================================================
121
+ // A class for rendering text
122
+ //==================================================================================
123
+ class DECLSPEC sge_text: public sge_TextEditor
124
+ {
125
+ protected:
126
+ #ifndef _SGE_NOTTF
127
+ sge_TTFont *tt_font; //The truetype font
128
+ #else
129
+ Uint8 *tt_font;
130
+ #endif
131
+
132
+ //TT Font color
133
+ SDL_Color color;
134
+ SDL_Color background;
135
+
136
+ sge_bmpFont *bm_font; //The bitmap font
137
+
138
+ Uint8 alpha_level; //Alpha level (default: opaque)
139
+
140
+ SDL_Surface* text_surface;
141
+ virtual void set_textSurface(SDL_Surface *new_surf){;}
142
+
143
+ //Use what render?
144
+ bool use_tt;
145
+
146
+ //Show cursor when rendering text?
147
+ bool sCursor;
148
+
149
+ public:
150
+ //Constructor
151
+ sge_text(void){tt_font=NULL; bm_font=NULL; text_surface=NULL; use_tt=true; text_surface=NULL; sCursor=false; alpha_level=SDL_ALPHA_OPAQUE;}
152
+ virtual ~sge_text(void){if(text_surface){SDL_FreeSurface(text_surface);}}
153
+
154
+ //Get a pointer to the text surface or (if copy=true) returns
155
+ //a copy (don't forget to free it later)
156
+ SDL_Surface* get_textSurface(bool copy=false);
157
+
158
+ //Updates the textsurface if the text has changed (or if force=true)
159
+ //and returns true if the surface was updated
160
+ bool update_textSurface(bool force=false);
161
+
162
+ #ifndef _SGE_NOTTF
163
+ void set_ttFont(sge_TTFont *font, Uint8 r, Uint8 g, Uint8 b, Uint8 br=0, Uint8 bg=0, Uint8 bb=0);
164
+ #endif
165
+
166
+ bool get_color(SDL_Color *fg){if( tt_font ) {fg->r = color.r; fg->g = color.g; fg->b = color.b; return true;} else return false;}
167
+ bool get_bg(SDL_Color *bg) {if( tt_font ) {bg->r = background.r; bg->g = background.g; bg->b = background.b; return true;} else return false;}
168
+
169
+ void set_bmFont(sge_bmpFont *bm_font);
170
+
171
+ //Should a cursor be drawn?
172
+ void show_cursor(bool mode){if(mode!=sCursor){text_changed=true;} sCursor=mode;}
173
+
174
+ //Render text to a surface
175
+ SDL_Rect render_text(SDL_Surface *surface, Sint16 x, Sint16 y);
176
+
177
+ void use_TTrender(void){if(tt_font){use_tt=true;}}
178
+ void use_BMrender(void){if(bm_font){use_tt=false;}}
179
+
180
+ //set alpha level (default: opaque)
181
+ void set_alpha(Uint8 alpha){alpha_level = alpha;}
182
+ };
183
+
184
+
185
+ //==================================================================================
186
+ //sge_TextSurface (derived public from sge_text and sge_surface)
187
+ //sge_TextSsprite (derived public from sge_text and sge_ssprite)
188
+ //sge_TextSprite (derived public from sge_text and sge_sprite)
189
+ //==================================================================================
190
+ class DECLSPEC sge_TextSurface: public sge_text, public sge_surface
191
+ {
192
+ protected:
193
+ virtual void set_textSurface(SDL_Surface *new_surf);
194
+
195
+ public:
196
+ sge_TextSurface(SDL_Surface *screen, Sint16 x=0, Sint16 y=0):
197
+ sge_surface(screen,screen,x,y)
198
+ {\
199
+ surface=NULL;
200
+ current_pos.w=0; current_pos.h=0;
201
+ }
202
+
203
+ sge_TextSurface(SDL_Surface *screen, const std::string text, Sint16 x=0, Sint16 y=0):
204
+ sge_surface(screen,screen,x,y)
205
+ {
206
+ change_text(text);
207
+ current_pos.w=0; current_pos.h=0;
208
+ }
209
+
210
+ virtual void draw(void);
211
+ };
212
+
213
+
214
+ class DECLSPEC sge_TextSsprite: public sge_text, public sge_ssprite
215
+ {
216
+ protected:
217
+ virtual void set_textSurface(SDL_Surface *new_surf);
218
+
219
+ public:
220
+ sge_TextSsprite(SDL_Surface *screen, Sint16 x=0, Sint16 y=0):
221
+ sge_ssprite(screen,screen,x,y)
222
+ {\
223
+ surface=NULL;
224
+ current_pos.w=0; current_pos.h=0;
225
+ }
226
+
227
+ sge_TextSsprite(SDL_Surface *screen, const std::string text, Sint16 x=0, Sint16 y=0):
228
+ sge_ssprite(screen,screen,x,y)
229
+ {
230
+ change_text(text);
231
+ current_pos.w=0; current_pos.h=0;
232
+ }
233
+
234
+ virtual void draw(void);
235
+ };
236
+
237
+
238
+ class DECLSPEC sge_TextSprite: public sge_text, public sge_sprite
239
+ {
240
+ protected:
241
+ virtual void set_textSurface(SDL_Surface *new_surf);
242
+
243
+ public:
244
+ sge_TextSprite(SDL_Surface *screen, Sint16 x=0, Sint16 y=0):
245
+ sge_sprite(screen,screen,x,y)
246
+ {\
247
+ surface=NULL;
248
+ current_pos.w=0; current_pos.h=0;
249
+ }
250
+
251
+ sge_TextSprite(SDL_Surface *screen, const std::string text, Sint16 x=0, Sint16 y=0):
252
+ sge_sprite(screen,screen,x,y)
253
+ {
254
+ change_text(text);
255
+ current_pos.w=0; current_pos.h=0;
256
+ }
257
+
258
+ virtual void draw(void);
259
+ };
260
+
261
+
262
+ //==================================================================================
263
+ // A helper function for lazy users: blocking text input for sge_TextSurface
264
+ // objects.
265
+ // Flags is the same as for BM and TTF input (which now uses this function)
266
+ //==================================================================================
267
+ DECLSPEC int sge_text_input(sge_TextSurface *tc, Uint8 flags);
268
+
269
+ #endif /* _SGE_NO_CLASSES */
270
+ #endif /* sge_textpp_H */
@@ -0,0 +1,1456 @@
1
+ /*
2
+ * SDL Graphics Extension
3
+ * Text/TrueType font functions
4
+ *
5
+ * Started 990815
6
+ *
7
+ * License: LGPL v2+ (see the file LICENSE)
8
+ * (c)1999-2003 Anders Lindstr�m
9
+ *
10
+ * Uses the excellent FreeType 2 library, available at:
11
+ * http://www.freetype.org/
12
+ */
13
+
14
+ /*********************************************************************
15
+ * This library is free software; you can redistribute it and/or *
16
+ * modify it under the terms of the GNU Library General Public *
17
+ * License as published by the Free Software Foundation; either *
18
+ * version 2 of the License, or (at your option) any later version. *
19
+ *********************************************************************/
20
+
21
+ /*
22
+ * Most of this code is taken from the SDL ttf lib by Sam Lantinga
23
+ * <slouken@devolution.com>
24
+ */
25
+
26
+
27
+ #include "SDL.h"
28
+ #include "SDL_endian.h"
29
+ #include <stdlib.h>
30
+ #include <string.h>
31
+ #include <stdarg.h>
32
+ #include <math.h>
33
+ #include "sge_surface.h"
34
+ #include "sge_primitives.h"
35
+ #include "sge_tt_text.h"
36
+ #include "sge_textpp.h"
37
+
38
+ #ifndef _SGE_NOTTF
39
+ #include <freetype/freetype.h>
40
+ #include <freetype/ftoutln.h>
41
+ #include <freetype/ttnameid.h>
42
+ #include <freetype/internal/ftobjs.h>
43
+
44
+ /* The structure used to hold glyph information (cached) */
45
+ struct glyph {
46
+ int stored;
47
+ FT_UInt index;
48
+ //FT_Bitmap bitmap;
49
+ FT_Bitmap pixmap;
50
+ int minx;
51
+ int maxx;
52
+ int miny;
53
+ int maxy;
54
+ int yoffset;
55
+ int advance;
56
+ Uint16 cached;
57
+ };
58
+
59
+ /* the truetype font structure */
60
+ struct _sge_TTFont{
61
+ FT_Face face;
62
+
63
+ /* Font metrics */
64
+ int height;
65
+ int ascent;
66
+ int descent;
67
+ int lineskip;
68
+
69
+ /* The font style */
70
+ Uint8 style;
71
+
72
+ /* Extra width in glyph bounds for text styles */
73
+ int glyph_overhang;
74
+ float glyph_italics;
75
+
76
+ /* Information in the font for underlining */
77
+ int underline_offset;
78
+ int underline_height;
79
+
80
+ /* For now, support Latin-1 character set caching */
81
+ glyph *current;
82
+ glyph cache[256];
83
+ glyph scratch;
84
+
85
+ /* We are responsible for closing the font stream */
86
+ SDL_RWops *src;
87
+ int freesrc;
88
+ FT_Open_Args args;
89
+
90
+ /* For non-scalable formats, we must remember which font index size */
91
+ int font_size_family;
92
+ };
93
+
94
+
95
+ /* FIXME: Right now we assume the gray-scale renderer Freetype is using
96
+ supports 256 shades of gray, but we should instead key off of num_grays
97
+ in the result FT_Bitmap after the FT_Render_Glyph() call. */
98
+ #define NUM_GRAYS 256
99
+
100
+ /* Handy routines for converting from fixed point */
101
+ #define FT_FLOOR(X) ((X & -64) / 64)
102
+ #define FT_CEIL(X) (((X + 63) & -64) / 64)
103
+
104
+ #define CACHED_METRICS 0x10
105
+ #define CACHED_BITMAP 0x01
106
+ #define CACHED_PIXMAP 0x02
107
+
108
+ /* Fix a problem with older version of Freetype */
109
+ #ifndef FT_OPEN_STREAM
110
+ #define FT_OPEN_STREAM ft_open_stream
111
+ #endif
112
+
113
+ /* The FreeType font engine/library */
114
+ static FT_Library _sge_library;
115
+ static int _sge_TTF_initialized = 0;
116
+ static int _sge_TTF_byteswapped = 0;
117
+
118
+ Uint8 _sge_TTF_AA=1; //Rendering mode: 0-OFF, 1-AA, 2-Alpha
119
+
120
+
121
+ /**********************************************************************************/
122
+ /** Open/misc font functions **/
123
+ /**********************************************************************************/
124
+
125
+ //==================================================================================
126
+ // Turns TTF AntiAliasing On/Off or alpha (nice but slow) (Default: On)
127
+ //==================================================================================
128
+ void sge_TTF_AAOff(void)
129
+ {
130
+ _sge_TTF_AA=0;
131
+ }
132
+ void sge_TTF_AAOn(void)
133
+ {
134
+ _sge_TTF_AA=1;
135
+ }
136
+ void sge_TTF_AA_Alpha(void)
137
+ {
138
+ _sge_TTF_AA=2;
139
+ }
140
+
141
+
142
+ //==================================================================================
143
+ // Control UNICODE byteswapping (default: no => swapped=0)
144
+ //==================================================================================
145
+ /* This function tells the library whether UNICODE text is generally
146
+ byteswapped. A UNICODE BOM character at the beginning of a string
147
+ will override this setting for that string.
148
+ */
149
+ void sge_TTF_ByteSwappedUNICODE(int swapped)
150
+ {
151
+ _sge_TTF_byteswapped = swapped;
152
+ }
153
+
154
+
155
+ //==================================================================================
156
+ // Closes the ttf engine, done by exit
157
+ //==================================================================================
158
+ void sge_TTF_Quit(void)
159
+ {
160
+ if ( _sge_TTF_initialized ) {
161
+ FT_Done_FreeType( _sge_library );
162
+ }
163
+ _sge_TTF_initialized = 0;
164
+ }
165
+
166
+
167
+ //==================================================================================
168
+ // Starts the ttf engine, must be called first
169
+ //==================================================================================
170
+ int sge_TTF_Init(void)
171
+ {
172
+ FT_Error error;
173
+
174
+ if( _sge_TTF_initialized )
175
+ return 0;
176
+
177
+ error = FT_Init_FreeType( &_sge_library );
178
+ if ( error ) {
179
+ SDL_SetError("SGE - Couldn't init FreeType engine");
180
+ return(-1);
181
+ } else {
182
+ _sge_TTF_initialized = 1;
183
+ }
184
+ atexit(sge_TTF_Quit); //dont't trust the user...
185
+ return 0;
186
+ }
187
+
188
+
189
+ //==================================================================================
190
+ // Some helper functions
191
+ //==================================================================================
192
+ void Flush_Glyph(glyph *glyph)
193
+ {
194
+ glyph->stored = 0;
195
+ glyph->index = 0;
196
+ //if( glyph->bitmap.buffer ) {
197
+ // free( glyph->bitmap.buffer );
198
+ // glyph->bitmap.buffer = 0;
199
+ //}
200
+ if( glyph->pixmap.buffer ) {
201
+ free( glyph->pixmap.buffer );
202
+ glyph->pixmap.buffer = 0;
203
+ }
204
+ glyph->cached = 0;
205
+ }
206
+
207
+ void Flush_Cache(sge_TTFont *font)
208
+ {
209
+ int i;
210
+ int size = sizeof( font->cache ) / sizeof( font->cache[0] );
211
+
212
+ for( i = 0; i < size; ++i ) {
213
+ if( font->cache[i].cached ) {
214
+ Flush_Glyph( &font->cache[i] );
215
+ }
216
+
217
+ }
218
+ if( font->scratch.cached ) {
219
+ Flush_Glyph( &font->scratch );
220
+ }
221
+ }
222
+
223
+
224
+ //==================================================================================
225
+ // Remove font from memory
226
+ //==================================================================================
227
+ void sge_TTF_CloseFont(sge_TTFont *font)
228
+ {
229
+ Flush_Cache( font );
230
+
231
+ if ( font->face )
232
+ FT_Done_Face( font->face );
233
+ if ( font->args.stream )
234
+ free( font->args.stream );
235
+ if ( font->freesrc )
236
+ SDL_RWclose( font->src );
237
+
238
+ free( font );
239
+ }
240
+
241
+
242
+ //==================================================================================
243
+ // Seek and read stream (internal)
244
+ //==================================================================================
245
+ unsigned long RWread(FT_Stream stream, unsigned long offset, unsigned char* buffer, unsigned long count)
246
+ {
247
+ SDL_RWops *src;
248
+
249
+ src = (SDL_RWops *)stream->descriptor.pointer;
250
+ SDL_RWseek( src, (int)offset, SEEK_SET );
251
+ return SDL_RWread( src, buffer, 1, (int)count );
252
+ }
253
+
254
+
255
+ //==================================================================================
256
+ // Open the TT font sream and returns the font
257
+ //==================================================================================
258
+ sge_TTFont *sge_TTF_OpenFontIndexRW(SDL_RWops *src, int freesrc, int ptsize, long index, int xdpi, int ydpi)
259
+ {
260
+ sge_TTFont *font;
261
+ FT_Error error;
262
+ FT_Face face;
263
+ FT_Fixed scale;
264
+ FT_Stream stream;
265
+ int position;
266
+
267
+ if( !_sge_TTF_initialized){
268
+ SDL_SetError("SGE - Freetype not initialized");
269
+ return NULL;
270
+ }
271
+
272
+ /* Check to make sure we can seek in this stream */
273
+ position = SDL_RWtell(src);
274
+ if ( position < 0 ) {
275
+ SDL_SetError("SGE - Can't seek in font stream");
276
+ return NULL;
277
+ }
278
+
279
+ font = (sge_TTFont *)malloc(sizeof(*font));
280
+ if ( font == NULL ) {
281
+ SDL_SetError("SGE - Out of memory");
282
+ return(NULL);
283
+ }
284
+ memset(font, 0, sizeof(*font));
285
+
286
+ font->src = src;
287
+ font->freesrc = freesrc;
288
+
289
+ stream = (FT_Stream)malloc(sizeof(*stream));
290
+ if ( stream == NULL ) {
291
+ SDL_SetError("SGE - Out of memory");
292
+ sge_TTF_CloseFont( font );
293
+ return NULL;
294
+ }
295
+ memset(stream, 0, sizeof(*stream));
296
+
297
+ stream->memory = _sge_library->memory;
298
+ stream->read = RWread;
299
+ stream->descriptor.pointer = src;
300
+ stream->pos = (unsigned long)position;
301
+ SDL_RWseek(src, 0, SEEK_END);
302
+ stream->size = (unsigned long)(SDL_RWtell(src) - position);
303
+ SDL_RWseek(src, position, SEEK_SET);
304
+
305
+ font->args.flags = FT_OPEN_STREAM;
306
+ font->args.stream = stream;
307
+
308
+ /* Open the font stream and create ancillary data */
309
+ error = FT_Open_Face( _sge_library, &font->args, index, &font->face );
310
+ if ( error ) {
311
+ SDL_SetError("SGE - Couldn't open font face");
312
+ sge_TTF_CloseFont( font );
313
+ return NULL;
314
+ }
315
+ face = font->face;
316
+
317
+ /* Handle scalable font face (global metrics) */
318
+ if ( FT_IS_SCALABLE(face) ) {
319
+
320
+ /* Set the character size and use DPI in arguments */
321
+ error = FT_Set_Char_Size( font->face, 0, ptsize * 64, xdpi, ydpi );
322
+ if( error ) {
323
+ SDL_SetError("SGE - Couldn't set font size");
324
+ sge_TTF_CloseFont( font );
325
+ return NULL;
326
+ }
327
+
328
+ /* Get the scalable font metrics for this font */
329
+ scale = face->size->metrics.y_scale;
330
+ font->ascent = FT_CEIL(FT_MulFix(face->bbox.yMax, scale));
331
+ font->descent = FT_CEIL(FT_MulFix(face->bbox.yMin, scale));
332
+ font->height = font->ascent - font->descent + /* baseline */ 1;
333
+ font->lineskip = FT_CEIL(FT_MulFix(face->height, scale));
334
+ font->underline_offset = FT_FLOOR(FT_MulFix(face->underline_position, scale));
335
+ font->underline_height = FT_FLOOR(FT_MulFix(face->underline_thickness, scale));
336
+ } else {
337
+ /* Non-scalable font face. ptsize determines which family
338
+ * or series of fonts to grab from the non-scalable format.
339
+ * It is not the point size of the font.
340
+ * */
341
+ if ( ptsize >= font->face->num_fixed_sizes )
342
+ ptsize = font->face->num_fixed_sizes - 1;
343
+
344
+ font->font_size_family = ptsize;
345
+ error = FT_Set_Pixel_Sizes( face, face->available_sizes[ptsize].height, face->available_sizes[ptsize].width );
346
+
347
+ /* With non-scalale fonts, Freetype2 likes to fill many of the
348
+ * font metrics with the value of 0. The size of the
349
+ * non-scalable fonts must be determined differently
350
+ * or sometimes cannot be determined.
351
+ * */
352
+ font->ascent = face->available_sizes[ptsize].height;
353
+ font->descent = 0;
354
+ font->height = face->available_sizes[ptsize].height;
355
+ font->lineskip = FT_CEIL(font->ascent);
356
+ font->underline_offset = FT_FLOOR(face->underline_position);
357
+ font->underline_height = FT_FLOOR(face->underline_thickness);
358
+ }
359
+
360
+ if ( font->underline_height < 1 )
361
+ font->underline_height = 1;
362
+
363
+ /* Set the default font style */
364
+ font->style = SGE_TTF_NORMAL;
365
+ font->glyph_overhang = face->size->metrics.y_ppem / 10;
366
+ /* x offset = cos(((90.0-12)/360)*2*M_PI), or 12 degree angle */
367
+ font->glyph_italics = 0.207f;
368
+ font->glyph_italics *= font->height;
369
+
370
+ return font;
371
+ }
372
+
373
+ sge_TTFont *sge_TTF_OpenFontRW( SDL_RWops *src, int freesrc, int ptsize, int xdpi, int ydpi)
374
+ {
375
+ return sge_TTF_OpenFontIndexRW(src, freesrc, ptsize, 0, xdpi, ydpi);
376
+ }
377
+
378
+ sge_TTFont *sge_TTF_OpenFontIndex( const char *file, int ptsize, long index, int xdpi, int ydpi)
379
+ {
380
+ return sge_TTF_OpenFontIndexRW(SDL_RWFromFile(file, "rb"), 1, ptsize, index, xdpi, ydpi);
381
+ }
382
+
383
+ sge_TTFont *sge_TTF_OpenFont(const char *file, int ptsize)
384
+ {
385
+ return sge_TTF_OpenFontIndex(file, ptsize, 0, 96, 96);
386
+ }
387
+
388
+
389
+ //==================================================================================
390
+ // Load a glyph
391
+ //==================================================================================
392
+ FT_Error Load_Glyph(sge_TTFont *font, Uint16 ch, glyph *cached, int want )
393
+ {
394
+ FT_Face face;
395
+ FT_Error error;
396
+ FT_GlyphSlot glyph;
397
+ FT_Glyph_Metrics* metrics;
398
+ FT_Outline* outline;
399
+
400
+ if ( !font || !font->face ) {
401
+ return FT_Err_Invalid_Handle;
402
+ }
403
+
404
+ face = font->face;
405
+
406
+ /* Load the glyph */
407
+ if ( ! cached->index ) {
408
+ cached->index = FT_Get_Char_Index( face, ch );
409
+ }
410
+ error = FT_Load_Glyph( face, cached->index, FT_LOAD_DEFAULT );
411
+ if( error ) {
412
+ return error;
413
+ }
414
+
415
+ /* Get our glyph shortcuts */
416
+ glyph = face->glyph;
417
+ metrics = &glyph->metrics;
418
+ outline = &glyph->outline;
419
+
420
+ /* Get the glyph metrics if desired */
421
+ if ( (want & CACHED_METRICS) && !(cached->stored & CACHED_METRICS) ) {
422
+ if ( FT_IS_SCALABLE( face ) ) {
423
+ /* Get the bounding box */
424
+ cached->minx = FT_FLOOR(metrics->horiBearingX);
425
+ cached->maxx = cached->minx + FT_CEIL(metrics->width);
426
+ cached->maxy = FT_FLOOR(metrics->horiBearingY);
427
+ cached->miny = cached->maxy - FT_CEIL(metrics->height);
428
+ cached->yoffset = font->ascent - cached->maxy;
429
+ cached->advance = FT_CEIL(metrics->horiAdvance);
430
+ } else {
431
+ /* Get the bounding box for non-scalable format.
432
+ * Again, freetype2 fills in many of the font metrics
433
+ * with the value of 0, so some of the values we
434
+ * need must be calculated differently with certain
435
+ * assumptions about non-scalable formats.
436
+ * */
437
+ cached->minx = FT_FLOOR(metrics->horiBearingX);
438
+ cached->maxx = cached->minx + FT_CEIL(metrics->horiAdvance);
439
+ cached->maxy = FT_FLOOR(metrics->horiBearingY);
440
+ cached->miny = cached->maxy - FT_CEIL(face->available_sizes[font->font_size_family].height);
441
+ cached->yoffset = 0;
442
+ cached->advance = FT_CEIL(metrics->horiAdvance);
443
+ }
444
+
445
+ /* Adjust for bold and italic text */
446
+ if ( font->style & SGE_TTF_BOLD ) {
447
+ cached->maxx += font->glyph_overhang;
448
+ }
449
+ if ( font->style & SGE_TTF_ITALIC ) {
450
+ cached->maxx += (int)ceil(font->glyph_italics);
451
+ }
452
+ cached->stored |= CACHED_METRICS;
453
+ }
454
+
455
+ if ( ((want & CACHED_BITMAP) && !(cached->stored & CACHED_BITMAP)) ||
456
+ ((want & CACHED_PIXMAP) && !(cached->stored & CACHED_PIXMAP)) ) {
457
+ //int mono = (want & CACHED_BITMAP);
458
+ int i;
459
+ FT_Bitmap* src;
460
+ FT_Bitmap* dst;
461
+
462
+ /* Handle the italic style */
463
+ if( font->style & SGE_TTF_ITALIC ) {
464
+ FT_Matrix shear;
465
+
466
+ shear.xx = 1 << 16;
467
+ shear.xy = (int) ( font->glyph_italics * ( 1 << 16 ) ) / font->height;
468
+ shear.yx = 0;
469
+ shear.yy = 1 << 16;
470
+
471
+ FT_Outline_Transform( outline, &shear );
472
+ }
473
+
474
+ /* Render the glyph */
475
+ //if ( mono ) {
476
+ // error = FT_Render_Glyph( glyph, ft_render_mode_mono );
477
+ //} else {
478
+ error = FT_Render_Glyph( glyph, ft_render_mode_normal );
479
+ //}
480
+ if( error ) {
481
+ return error;
482
+ }
483
+
484
+ /* Copy over information to cache */
485
+ src = &glyph->bitmap;
486
+ //if ( mono ) {
487
+ // dst = &cached->bitmap;
488
+ //} else {
489
+ dst = &cached->pixmap;
490
+ //}
491
+ memcpy( dst, src, sizeof( *dst ) );
492
+
493
+ /* FT_Render_Glyph() and .fon fonts always generate a
494
+ * two-color (black and white) glyphslot surface, even
495
+ * when rendered in ft_render_mode_normal. This is probably
496
+ * a freetype2 bug because it is inconsistent with the
497
+ * freetype2 documentation under FT_Render_Mode section.
498
+ * */
499
+ if ( !FT_IS_SCALABLE(face) ) {
500
+ dst->pitch *= 8;
501
+ }
502
+
503
+ /* Adjust for bold and italic text */
504
+ if( font->style & SGE_TTF_BOLD ) {
505
+ int bump = font->glyph_overhang;
506
+ dst->pitch += bump;
507
+ dst->width += bump;
508
+ }
509
+ if( font->style & SGE_TTF_ITALIC ) {
510
+ int bump = (int)ceil(font->glyph_italics);
511
+ dst->pitch += bump;
512
+ dst->width += bump;
513
+ }
514
+
515
+ if( dst->rows != 0 ) {
516
+ dst->buffer = (unsigned char *)malloc( dst->pitch * dst->rows );
517
+ if( !dst->buffer ) {
518
+ return FT_Err_Out_Of_Memory;
519
+ }
520
+ memset( dst->buffer, 0, dst->pitch * dst->rows );
521
+
522
+ for( i = 0; i < src->rows; i++ ) {
523
+ int soffset = i * src->pitch;
524
+ int doffset = i * dst->pitch;
525
+ /*if ( mono ) {
526
+ unsigned char *srcp = src->buffer + soffset;
527
+ unsigned char *dstp = dst->buffer + doffset;
528
+ int j;
529
+ for ( j = 0; j < src->width; j += 8 ) {
530
+ unsigned char ch = *srcp++;
531
+ *dstp++ = (ch&0x80) >> 7;
532
+ ch <<= 1;
533
+ *dstp++ = (ch&0x80) >> 7;
534
+ ch <<= 1;
535
+ *dstp++ = (ch&0x80) >> 7;
536
+ ch <<= 1;
537
+ *dstp++ = (ch&0x80) >> 7;
538
+ ch <<= 1;
539
+ *dstp++ = (ch&0x80) >> 7;
540
+ ch <<= 1;
541
+ *dstp++ = (ch&0x80) >> 7;
542
+ ch <<= 1;
543
+ *dstp++ = (ch&0x80) >> 7;
544
+ ch <<= 1;
545
+ *dstp++ = (ch&0x80) >> 7;
546
+ }
547
+ } else */if ( !FT_IS_SCALABLE(face) ) {
548
+ /* This special case wouldn't
549
+ * be here if the FT_Render_Glyph()
550
+ * function wasn't buggy when it tried
551
+ * to render a .fon font with 256
552
+ * shades of gray. Instead, it
553
+ * returns a black and white surface
554
+ * and we have to translate it back
555
+ * to a 256 gray shaded surface.
556
+ * */
557
+ unsigned char *srcp = src->buffer + soffset;
558
+ unsigned char *dstp = dst->buffer + doffset;
559
+ unsigned char ch;
560
+ int j, k;
561
+ for ( j = 0; j < src->width; j += 8) {
562
+ ch = *srcp++;
563
+ for (k = 0; k < 8; ++k) {
564
+ if ((ch&0x80) >> 7) {
565
+ *dstp++ = NUM_GRAYS - 1;
566
+ } else {
567
+ *dstp++ = 0x00;
568
+ }
569
+ ch <<= 1;
570
+ }
571
+ }
572
+ } else {
573
+ memcpy(dst->buffer+doffset,
574
+ src->buffer+soffset, src->pitch);
575
+ }
576
+ }
577
+ }
578
+
579
+ /* Handle the bold style */
580
+ if ( font->style & SGE_TTF_BOLD ) {
581
+ int row;
582
+ int col;
583
+ int offset;
584
+ int pixel;
585
+ Uint8* pixmap;
586
+
587
+ /* The pixmap is a little hard, we have to add and clamp */
588
+ for( row = dst->rows - 1; row >= 0; --row ) {
589
+ pixmap = (Uint8*) dst->buffer + row * dst->pitch;
590
+ for( offset=1; offset <= font->glyph_overhang; ++offset ) {
591
+ for( col = dst->width - 1; col > 0; --col ) {
592
+ pixel = (pixmap[col] + pixmap[col-1]);
593
+ if( pixel > NUM_GRAYS - 1 ) {
594
+ pixel = NUM_GRAYS - 1;
595
+ }
596
+ pixmap[col] = (Uint8) pixel;
597
+ }
598
+ }
599
+ }
600
+ }
601
+
602
+ /* Mark that we rendered this format */
603
+ //if ( mono ) {
604
+ // cached->stored |= CACHED_BITMAP;
605
+ //} else {
606
+ cached->stored |= CACHED_PIXMAP;
607
+ //}
608
+ }
609
+
610
+ /* We're done, mark this glyph cached */
611
+ cached->cached = ch;
612
+
613
+ return 0;
614
+ }
615
+
616
+
617
+ //==================================================================================
618
+ // Find glyph
619
+ //==================================================================================
620
+ FT_Error Find_Glyph(sge_TTFont *font, Uint16 ch, int want)
621
+ {
622
+ int retval = 0;
623
+
624
+ if( ch < 256 ) {
625
+ font->current = &font->cache[ch];
626
+ } else {
627
+ if ( font->scratch.cached != ch ) {
628
+ Flush_Glyph( &font->scratch );
629
+ }
630
+ font->current = &font->scratch;
631
+ }
632
+ if ( (font->current->stored & want) != want ) {
633
+ retval = Load_Glyph( font, ch, font->current, want );
634
+ }
635
+ return retval;
636
+ }
637
+
638
+
639
+ //==================================================================================
640
+ // Change the size of font
641
+ //==================================================================================
642
+ int sge_TTF_SetFontSizeDPI(sge_TTFont *font, int ptsize, int xdpi, int ydpi)
643
+ {
644
+ FT_Error error;
645
+ FT_Fixed scale;
646
+ FT_Face face;
647
+
648
+ face = font->face;
649
+ Flush_Cache(font);
650
+
651
+ if ( FT_IS_SCALABLE(face) ) {
652
+
653
+ /* Set the character size */
654
+ error = FT_Set_Char_Size( font->face, 0, ptsize * 64, xdpi, ydpi );
655
+ if( error ) {
656
+ sge_SetError("SGE - Couldn't set font size");
657
+ sge_TTF_CloseFont( font );
658
+ return -1;
659
+ }
660
+
661
+ /* Get the scalable font metrics for this font */
662
+ scale = face->size->metrics.y_scale;
663
+ font->ascent = FT_CEIL(FT_MulFix(face->bbox.yMax, scale));
664
+ font->descent = FT_CEIL(FT_MulFix(face->bbox.yMin, scale));
665
+ font->height = font->ascent - font->descent + /* baseline */ 1;
666
+ font->lineskip = FT_CEIL(FT_MulFix(face->height, scale));
667
+ font->underline_offset = FT_FLOOR(FT_MulFix(face->underline_position, scale));
668
+ font->underline_height = FT_FLOOR(FT_MulFix(face->underline_thickness, scale));
669
+
670
+ } else {
671
+ /* Non-scalable font case. ptsize determines which family
672
+ * or series of fonts to grab from the non-scalable format.
673
+ * It is not the point size of the font.
674
+ * */
675
+ if ( ptsize >= font->face->num_fixed_sizes )
676
+ ptsize = font->face->num_fixed_sizes - 1;
677
+
678
+ font->font_size_family = ptsize;
679
+ error = FT_Set_Pixel_Sizes( face, face->available_sizes[ptsize].height, face->available_sizes[ptsize].width );
680
+
681
+ /* With non-scalale fonts, Freetype2 likes to fill many of the
682
+ * font metrics with the value of 0. The size of the
683
+ * non-scalable fonts must be determined differently
684
+ * or sometimes cannot be determined.
685
+ * */
686
+ font->ascent = face->available_sizes[ptsize].height;
687
+ font->descent = 0;
688
+ font->height = face->available_sizes[ptsize].height;
689
+ font->lineskip = FT_CEIL(font->ascent);
690
+ font->underline_offset = FT_FLOOR(face->underline_position);
691
+ font->underline_height = FT_FLOOR(face->underline_thickness);
692
+ }
693
+
694
+ if ( font->underline_height < 1 ) {
695
+ font->underline_height = 1;
696
+ }
697
+
698
+ /* Set the default font style */
699
+ //font->style = SGE_TTF_NORMAL;
700
+ font->glyph_overhang = face->size->metrics.y_ppem / 10;
701
+ /* x offset = cos(((90.0-12)/360)*2*M_PI), or 12 degree angle */
702
+ font->glyph_italics = 0.207f;
703
+ font->glyph_italics *= font->height;
704
+
705
+ return 0;
706
+ }
707
+
708
+ int sge_TTF_SetFontSize(sge_TTFont *font, int ptsize)
709
+ {
710
+ return sge_TTF_SetFontSizeDPI(font, ptsize, 96 ,96);
711
+ }
712
+
713
+
714
+ //==================================================================================
715
+ // Get font geometrics
716
+ //==================================================================================
717
+ int sge_TTF_FontHeight(sge_TTFont *font)
718
+ {
719
+ return(font->height);
720
+ }
721
+ int sge_TTF_FontAscent(sge_TTFont *font)
722
+ {
723
+ return(font->ascent);
724
+ }
725
+ int sge_TTF_FontDescent(sge_TTFont *font)
726
+ {
727
+ return(font->descent);
728
+ }
729
+ int sge_TTF_FontLineSkip(sge_TTFont *font)
730
+ {
731
+ return(font->lineskip);
732
+ }
733
+ long sge_TTF_FontFaces(sge_TTFont *font)
734
+ {
735
+ return(font->face->num_faces);
736
+ }
737
+ int sge_TTF_FontFaceIsFixedWidth(sge_TTFont *font)
738
+ {
739
+ return(FT_IS_FIXED_WIDTH(font->face));
740
+ }
741
+ char *sge_TTF_FontFaceFamilyName(sge_TTFont *font)
742
+ {
743
+ return(font->face->family_name);
744
+ }
745
+ char *sge_TTF_FontFaceStyleName(sge_TTFont *font)
746
+ {
747
+ return(font->face->style_name);
748
+ }
749
+ int sge_TTF_GlyphMetrics(sge_TTFont *font, Uint16 ch, int* minx, int* maxx, int* miny, int* maxy, int* advance)
750
+ {
751
+ FT_Error error;
752
+
753
+ error = Find_Glyph(font, ch, CACHED_METRICS);
754
+
755
+ if ( error ) {
756
+ return -1;
757
+ }
758
+
759
+ if ( minx ) {
760
+ *minx = font->current->minx;
761
+ }
762
+ if ( maxx ) {
763
+ *maxx = font->current->maxx;
764
+ }
765
+ if ( miny ) {
766
+ *miny = font->current->miny;
767
+ }
768
+ if ( maxy ) {
769
+ *maxy = font->current->maxy;
770
+ }
771
+ if ( advance ) {
772
+ *advance = font->current->advance;
773
+ }
774
+ return 0;
775
+ }
776
+
777
+
778
+ //==================================================================================
779
+ // Set font style
780
+ //==================================================================================
781
+ void sge_TTF_SetFontStyle(sge_TTFont *font, Uint8 style)
782
+ {
783
+ font->style = style;
784
+ Flush_Cache(font);
785
+ }
786
+
787
+
788
+ //==================================================================================
789
+ // Get font style
790
+ //==================================================================================
791
+ Uint8 sge_TTF_GetFontStyle(sge_TTFont *font)
792
+ {
793
+ return(font->style);
794
+ }
795
+ #endif /* _SGE_NOTTF */
796
+
797
+
798
+ //==================================================================================
799
+ // Convert the Latin-1 text to UNICODE
800
+ //==================================================================================
801
+ Uint16 *ASCII_to_UNICODE(Uint16 *unicode, const char *text, int len)
802
+ {
803
+ int i;
804
+
805
+ for ( i=0; i < len; ++i ) {
806
+ unicode[i] = ((const unsigned char *)text)[i];
807
+ }
808
+ unicode[i] = 0;
809
+
810
+ return unicode;
811
+ }
812
+
813
+ Uint16 *sge_Latin1_Uni(const char *text)
814
+ {
815
+ Uint16 *unicode_text;
816
+ int i, unicode_len;
817
+
818
+ /* Copy the Latin-1 text to a UNICODE text buffer */
819
+ unicode_len = strlen(text);
820
+ unicode_text = (Uint16 *)malloc((unicode_len+1)*(sizeof *unicode_text));
821
+ if ( unicode_text == NULL ) {
822
+ SDL_SetError("SGE - Out of memory");
823
+ return(NULL);
824
+ }
825
+ for ( i=0; i < unicode_len; ++i ) {
826
+ unicode_text[i] = ((const unsigned char *)text)[i];
827
+ }
828
+ unicode_text[i] = 0;
829
+
830
+ return(unicode_text);
831
+ }
832
+
833
+ //==================================================================================
834
+ // Convert the UTF-8 text to UNICODE
835
+ //==================================================================================
836
+ Uint16 *UTF8_to_UNICODE(Uint16 *unicode, const char *utf8, int len)
837
+ {
838
+ int i, j;
839
+ Uint16 ch;
840
+
841
+ for ( i=0, j=0; i < len; ++i, ++j ) {
842
+ ch = ((const unsigned char *)utf8)[i];
843
+ if ( ch >= 0xF0 ) {
844
+ ch = (Uint16)(utf8[i]&0x07) << 18;
845
+ ch |= (Uint16)(utf8[++i]&0x3F) << 12;
846
+ ch |= (Uint16)(utf8[++i]&0x3F) << 6;
847
+ ch |= (Uint16)(utf8[++i]&0x3F);
848
+ } else
849
+ if ( ch >= 0xE0 ) {
850
+ ch = (Uint16)(utf8[i]&0x3F) << 12;
851
+ ch |= (Uint16)(utf8[++i]&0x3F) << 6;
852
+ ch |= (Uint16)(utf8[++i]&0x3F);
853
+ } else
854
+ if ( ch >= 0xC0 ) {
855
+ ch = (Uint16)(utf8[i]&0x3F) << 6;
856
+ ch |= (Uint16)(utf8[++i]&0x3F);
857
+ }
858
+ unicode[j] = ch;
859
+ }
860
+ unicode[j] = 0;
861
+
862
+ return unicode;
863
+ }
864
+
865
+ Uint16 *sge_UTF8_Uni(const char *text)
866
+ {
867
+ Uint16 *unicode_text;
868
+ int unicode_len;
869
+
870
+ /* Copy the UTF-8 text to a UNICODE text buffer */
871
+ unicode_len = strlen(text);
872
+ unicode_text = (Uint16 *)malloc((unicode_len+1)*(sizeof *unicode_text));
873
+ if ( unicode_text == NULL ) {
874
+ SDL_SetError("SGE - Out of memory");
875
+ return(NULL);
876
+ }
877
+
878
+ return UTF8_to_UNICODE(unicode_text, text, unicode_len);
879
+ }
880
+
881
+ #ifndef _SGE_NOTTF
882
+ //==================================================================================
883
+ // Get the width of the text with the given font
884
+ //==================================================================================
885
+ SDL_Rect sge_TTF_TextSizeUNI(sge_TTFont *font, const Uint16 *text)
886
+ {
887
+ SDL_Rect ret; ret.x=0; ret.y=0, ret.w=0, ret.h=0;
888
+ const Uint16 *ch;
889
+ int swapped;
890
+ int x, z;
891
+ int minx, maxx;
892
+ int miny, maxy;
893
+ glyph *glyph;
894
+ FT_Error error;
895
+
896
+ /* Initialize everything to 0 */
897
+ if ( ! _sge_TTF_initialized ) {
898
+ return ret;
899
+ }
900
+
901
+ minx = miny = 0;
902
+ maxx = maxy = 0;
903
+ swapped = _sge_TTF_byteswapped;
904
+
905
+ /* Load each character and sum it's bounding box */
906
+ x= 0;
907
+ for ( ch=text; *ch; ++ch ) {
908
+ Uint16 c = *ch;
909
+ if ( c == UNICODE_BOM_NATIVE ) {
910
+ swapped = 0;
911
+ if ( text == ch ) {
912
+ ++text;
913
+ }
914
+ continue;
915
+ }
916
+ if ( c == UNICODE_BOM_SWAPPED ) {
917
+ swapped = 1;
918
+ if ( text == ch ) {
919
+ ++text;
920
+ }
921
+ continue;
922
+ }
923
+ if ( swapped ) {
924
+ c = SDL_Swap16(c);
925
+ }
926
+
927
+ error = Find_Glyph(font, c, CACHED_METRICS);
928
+ if ( error ) {
929
+ return ret;
930
+ }
931
+ glyph = font->current;
932
+
933
+ if ( (ch == text) && (glyph->minx < 0) ) {
934
+ /* Fixes the texture wrapping bug when the first letter
935
+ * has a negative minx value or horibearing value. The entire
936
+ * bounding box must be adjusted to be bigger so the entire
937
+ * letter can fit without any texture corruption or wrapping.
938
+ *
939
+ * Effects: First enlarges bounding box.
940
+ * Second, xstart has to start ahead of its normal spot in the
941
+ * negative direction of the negative minx value.
942
+ * (pushes everything to the right).
943
+ *
944
+ * This will make the memory copy of the glyph bitmap data
945
+ * work out correctly.
946
+ * */
947
+ z -= glyph->minx;
948
+ }
949
+
950
+ z = x + glyph->minx;
951
+ if ( minx > z ) {
952
+ minx = z;
953
+ }
954
+ if ( font->style & SGE_TTF_BOLD ) {
955
+ x += font->glyph_overhang;
956
+ }
957
+ if ( glyph->advance > glyph->maxx ) {
958
+ z = x + glyph->advance;
959
+ } else {
960
+ z = x + glyph->maxx;
961
+ }
962
+ if ( maxx < z ) {
963
+ maxx = z;
964
+ }
965
+ x += glyph->advance;
966
+
967
+ if ( glyph->miny < miny ) {
968
+ miny = glyph->miny;
969
+ }
970
+ if ( glyph->maxy > maxy ) {
971
+ maxy = glyph->maxy;
972
+ }
973
+ }
974
+
975
+ /* Fill the bounds rectangle */
976
+ ret.w = (maxx - minx);
977
+ //ret.h = (maxy - miny); /* This is correct, but breaks many applications */
978
+ ret.h = font->height;
979
+
980
+ return ret;
981
+ }
982
+
983
+ SDL_Rect sge_TTF_TextSize(sge_TTFont *font, char *text)
984
+ {
985
+ SDL_Rect ret; ret.x=ret.y=ret.w=ret.y=0;
986
+ Uint16 *unicode_text;
987
+ int unicode_len;
988
+
989
+ /* Copy the Latin-1 text to a UNICODE text buffer */
990
+ unicode_len = strlen(text);
991
+ unicode_text = (Uint16 *)malloc((unicode_len+1)*(sizeof *unicode_text));
992
+ if ( unicode_text == NULL ) {
993
+ SDL_SetError("SGE - Out of memory");
994
+ return ret;
995
+ }
996
+ ASCII_to_UNICODE(unicode_text, text, unicode_len);
997
+
998
+ /* Render the new text */
999
+ ret = sge_TTF_TextSizeUNI(font, unicode_text);
1000
+
1001
+ /* Free the text buffer and return */
1002
+ free(unicode_text);
1003
+
1004
+ return ret;
1005
+ }
1006
+
1007
+
1008
+
1009
+ /**********************************************************************************/
1010
+ /** TTF output functions **/
1011
+ /**********************************************************************************/
1012
+
1013
+ //==================================================================================
1014
+ // TT Render (unicode)
1015
+ // Returns an 8bit or 32bit(8/8/8/8-alpha) surface with TT text
1016
+ //==================================================================================
1017
+ SDL_Surface *sge_TTF_Render(sge_TTFont *font,const Uint16 *text, SDL_Color fg, SDL_Color bg, int alpha_level)
1018
+ {
1019
+ int xstart, width;
1020
+ int w, h;
1021
+ SDL_Surface *textbuf;
1022
+ SDL_Palette *palette;
1023
+ int index;
1024
+ int rdiff, gdiff, bdiff;
1025
+ int swapped;
1026
+ const Uint16 *ch;
1027
+ Uint8 *src, *dst;
1028
+ Uint32 *dst32;
1029
+ Uint32 alpha=0;
1030
+ Uint32 pixel=0;
1031
+ Uint32 Rmask=0, Gmask=0, Bmask=0, Amask=0;
1032
+ int row, col;
1033
+ FT_Error error;
1034
+
1035
+ /* Get the dimensions of the text surface */
1036
+ SDL_Rect ret=sge_TTF_TextSizeUNI(font, text);
1037
+ w=ret.w; h=ret.h;
1038
+ if ( !w ) {
1039
+ SDL_SetError("SGE - Text has zero width");
1040
+ return(NULL);
1041
+ }
1042
+
1043
+ /* Create the target surface */
1044
+ width = w;
1045
+ if(_sge_TTF_AA!=2) /* Allocate an 8-bit pixmap */
1046
+ textbuf = SDL_AllocSurface(SDL_SWSURFACE, w, h, 8, 0, 0, 0, 0);
1047
+ else{ /* Allocate an 32-bit alpha pixmap */
1048
+ if ( SDL_BYTEORDER == SDL_LIL_ENDIAN ) {
1049
+ Rmask = 0x000000FF;
1050
+ Gmask = 0x0000FF00;
1051
+ Bmask = 0x00FF0000;
1052
+ Amask = 0xFF000000;
1053
+ } else {
1054
+ Rmask = 0xFF000000;
1055
+ Gmask = 0x00FF0000;
1056
+ Bmask = 0x0000FF00;
1057
+ Amask = 0x000000FF;
1058
+ }
1059
+ textbuf = SDL_AllocSurface(SDL_SWSURFACE, w, h, 32, Rmask, Gmask, Bmask, Amask);
1060
+ }
1061
+
1062
+ if ( textbuf == NULL ) {
1063
+ SDL_SetError("SGE - Out of memory");
1064
+ return(NULL);
1065
+ }
1066
+
1067
+
1068
+ /* Setup our colors */
1069
+ switch(_sge_TTF_AA){
1070
+
1071
+ case 0:{ /* No fancy antialiasing or alpha component */
1072
+ palette = textbuf->format->palette;
1073
+
1074
+ palette->colors[0].r = bg.r;
1075
+ palette->colors[0].g = bg.g;
1076
+ palette->colors[0].b = bg.b;
1077
+ palette->colors[1].r = fg.r;
1078
+ palette->colors[1].g = fg.g;
1079
+ palette->colors[1].b = fg.b;
1080
+ }
1081
+ break;
1082
+
1083
+ case 1:{ /* Fill the palette with NUM_GRAYS levels of shading from bg to fg */
1084
+ palette = textbuf->format->palette;
1085
+
1086
+ rdiff = fg.r - bg.r;
1087
+ gdiff = fg.g - bg.g;
1088
+ bdiff = fg.b - bg.b;
1089
+ for ( index=0; index< NUM_GRAYS; ++index ) {
1090
+ palette->colors[index].r = bg.r + (index*rdiff)/(NUM_GRAYS-1);
1091
+ palette->colors[index].g = bg.g + (index*gdiff)/(NUM_GRAYS-1);
1092
+ palette->colors[index].b = bg.b + (index*bdiff)/(NUM_GRAYS-1);
1093
+ }
1094
+ }
1095
+ break;
1096
+
1097
+ case 2:{ /* Alpha component magic */
1098
+ sge_ClearSurface(textbuf, SDL_MapRGBA(textbuf->format, bg.r,bg.g,bg.b,SDL_ALPHA_TRANSPARENT));
1099
+ //pixel = (fg.r<<16)|(fg.g<<8)|fg.b;
1100
+ pixel = (fg.b<<16)|(fg.g<<8)|fg.r;
1101
+ }
1102
+ break;
1103
+ }
1104
+
1105
+
1106
+ /* Load and render each character */
1107
+ xstart = 0;
1108
+ swapped = _sge_TTF_byteswapped;
1109
+ for ( ch=text; *ch; ++ch ) {
1110
+ Uint16 c = *ch;
1111
+ if ( c == UNICODE_BOM_NATIVE ) {
1112
+ swapped = 0;
1113
+ if ( text == ch ) {
1114
+ ++text;
1115
+ }
1116
+ continue;
1117
+ }
1118
+ if ( c == UNICODE_BOM_SWAPPED ) {
1119
+ swapped = 1;
1120
+ if ( text == ch ) {
1121
+ ++text;
1122
+ }
1123
+ continue;
1124
+ }
1125
+ if ( swapped ) {
1126
+ c = SDL_Swap16(c);
1127
+ }
1128
+
1129
+ error = Find_Glyph(font, c, CACHED_METRICS|CACHED_PIXMAP);
1130
+
1131
+ if ( ! error ) {
1132
+ /* Compensate for wrap around bug with negative minx's */
1133
+ if ( (ch == text) && (font->current->minx < 0) ) {
1134
+ xstart -= font->current->minx;
1135
+ }
1136
+
1137
+ w = font->current->pixmap.width;
1138
+ for ( row = 0; row < font->current->pixmap.rows; ++row ) {
1139
+ /* Make sure we don't go over the limit */
1140
+ if ( row+font->current->yoffset >= textbuf->h )
1141
+ continue;
1142
+
1143
+ dst = (Uint8 *)textbuf->pixels + (row + font->current->yoffset)* textbuf->pitch + xstart + font->current->minx;
1144
+
1145
+ switch(_sge_TTF_AA){
1146
+
1147
+ case 0:{ /* Normal */
1148
+ src = font->current->pixmap.buffer + row * font->current->pixmap.pitch;
1149
+ for ( col=w; col>0; --col ) {
1150
+ *dst++ |= (*src++<NUM_GRAYS/2)? 0:1;
1151
+ }
1152
+ }
1153
+ break;
1154
+ case 1:{ /* Antialiasing */
1155
+ src = font->current->pixmap.buffer + row * font->current->pixmap.pitch;
1156
+ for ( col=w; col>0; --col ) {
1157
+ *dst++ |= *src++;
1158
+ }
1159
+ }
1160
+ break;
1161
+
1162
+ case 2:{ /* Alpha */
1163
+ src = (Uint8*) (font->current->pixmap.buffer + font->current->pixmap.pitch * row);
1164
+ dst32 = (Uint32 *)textbuf->pixels + (row + font->current->yoffset)* textbuf->pitch/4 + xstart + font->current->minx;
1165
+ if( alpha_level == SDL_ALPHA_OPAQUE ){
1166
+ for ( col=w; col>0; --col ) {
1167
+ alpha = *src++;
1168
+ *dst32++ |= pixel | (alpha << 24);
1169
+ }
1170
+ }else{
1171
+ //We need to scale the alpha value
1172
+ //Thanks mabi!
1173
+ for ( col=w; col>0; --col ) {
1174
+ alpha = (*src++) * alpha_level/255;
1175
+ *dst32++ |= pixel | (alpha << 24);
1176
+ }
1177
+ }
1178
+ }
1179
+ break;
1180
+ }
1181
+ }
1182
+
1183
+ xstart += font->current->advance;
1184
+ if ( font->style & SGE_TTF_BOLD ) {
1185
+ xstart += font->glyph_overhang;
1186
+ }
1187
+ }
1188
+ }
1189
+
1190
+ /* Handle the underline style */
1191
+ if ( font->style & SGE_TTF_UNDERLINE ) {
1192
+ int row_offset;
1193
+
1194
+ row_offset = font->ascent - font->underline_offset - 1;
1195
+ if ( row_offset > textbuf->h ) {
1196
+ row_offset = (textbuf->h-1) - font->underline_height;
1197
+ }
1198
+
1199
+ if(_sge_TTF_AA==0){
1200
+ dst = (Uint8 *)textbuf->pixels + row_offset * textbuf->pitch;
1201
+ for ( row=font->underline_height; row>0; --row ) {
1202
+ memset(dst, 1, textbuf->w );
1203
+ dst += textbuf->pitch;
1204
+ }
1205
+ }else if(_sge_TTF_AA==1){
1206
+ dst = (Uint8 *)textbuf->pixels + row_offset * textbuf->pitch;
1207
+ for ( row=font->underline_height; row>0; --row ) {
1208
+ memset(dst, NUM_GRAYS - 1, textbuf->w );
1209
+ dst += textbuf->pitch;
1210
+ }
1211
+ }else{
1212
+ //pixel |= Amask;
1213
+ pixel |= (alpha_level << 24);
1214
+ dst32 = (Uint32 *)textbuf->pixels+row_offset*textbuf->pitch/4;
1215
+ for ( row=font->underline_height; row>0; --row ) {
1216
+ for ( col=0; col < textbuf->w; ++col ) {
1217
+ dst32[col] = pixel;
1218
+ }
1219
+ dst32 += textbuf->pitch/4;
1220
+ }
1221
+ }
1222
+ }
1223
+ return(textbuf);
1224
+ }
1225
+
1226
+ SDL_Surface *sge_TTF_RenderUNICODE(sge_TTFont *font,const Uint16 *text, SDL_Color fg, SDL_Color bg)
1227
+ {
1228
+ return sge_TTF_Render(font, text, fg, bg, SDL_ALPHA_OPAQUE);
1229
+ }
1230
+
1231
+ //==================================================================================
1232
+ // Renders the Unicode string to TrueType on surface, with the color fcolor.
1233
+ // bcolor is the target color for the antialiasing.
1234
+ // Alpha sets the transparency of the text (255-solid, 0-max).
1235
+ //==================================================================================
1236
+ SDL_Rect sge_tt_textout_UNI(SDL_Surface *Surface, sge_TTFont *font, const Uint16 *uni, Sint16 x, Sint16 y, Uint32 fcolor, Uint32 bcolor, int Alpha)
1237
+ {
1238
+ SDL_Rect ret; ret.x=0; ret.y=0; ret.w=0; ret.h=0;
1239
+
1240
+ SDL_Color temp;
1241
+ SDL_Surface *text;
1242
+
1243
+ text=sge_TTF_Render(font,uni,sge_GetRGB(Surface,fcolor),sge_GetRGB(Surface,bcolor), Alpha);
1244
+ if(text==NULL){return ret;}
1245
+
1246
+ /* Align the surface text to the baseline */
1247
+ Uint16 ascent=font->ascent;
1248
+
1249
+ temp=sge_GetRGB(Surface,bcolor);
1250
+ sge_BlitTransparent(text,Surface,0,0,x,y-ascent,text->w,text->h,SDL_MapRGB(text->format,temp.r,temp.g,temp.b),Alpha);
1251
+ sge_UpdateRect(Surface,x,y-ascent,text->w,text->h);
1252
+
1253
+ ret.x=x; ret.y=y-ascent; ret.w=text->w; ret.h=text->h;
1254
+
1255
+ SDL_FreeSurface(text);
1256
+ return ret;
1257
+ }
1258
+
1259
+
1260
+ //==================================================================================
1261
+ // Renders the Unicode string to TrueType on surface, with the color fcolor.
1262
+ // bcolor is the target color for the antialiasing.
1263
+ // Alpha sets the transparency of the text (0-solid, 255-max). (RGB)
1264
+ //==================================================================================
1265
+ SDL_Rect sge_tt_textout_UNI(SDL_Surface *Surface, sge_TTFont *font, const Uint16 *uni, Sint16 x, Sint16 y, Uint8 fR, Uint8 fG, Uint8 fB, Uint8 bR, Uint8 bG, Uint8 bB, int Alpha)
1266
+ {
1267
+ SDL_Rect ret; ret.x=0; ret.y=0; ret.w=0; ret.h=0;
1268
+ SDL_Surface *text;
1269
+
1270
+ text=sge_TTF_Render(font,uni,sge_FillPaletteEntry(fR,fG,fB),sge_FillPaletteEntry(bR,bG,bB), Alpha);
1271
+ if(text==NULL){return ret;}
1272
+
1273
+ /* Align the surface text to the baseline */
1274
+ Uint16 ascent=font->ascent;
1275
+
1276
+ sge_BlitTransparent(text,Surface,0,0,x,y-ascent,text->w,text->h,SDL_MapRGB(text->format,bR,bG,bB),Alpha);
1277
+
1278
+ sge_UpdateRect(Surface,x,y-ascent,text->w,text->h);
1279
+
1280
+ ret.x=x; ret.y=y-ascent; ret.w=text->w; ret.h=text->h;
1281
+
1282
+ SDL_FreeSurface(text);
1283
+ return ret;
1284
+ }
1285
+
1286
+
1287
+ //==================================================================================
1288
+ // Renders the Latin-1 string to TrueType on surface, with the color fcolor.
1289
+ // bcolor is the target color for the antialiasing.
1290
+ // Alpha sets the transparency of the text (0-solid, 255-max).
1291
+ //==================================================================================
1292
+ SDL_Rect sge_tt_textout(SDL_Surface *Surface, sge_TTFont *font, const char *string, Sint16 x, Sint16 y, Uint32 fcolor, Uint32 bcolor, int Alpha)
1293
+ {
1294
+ SDL_Rect ret;
1295
+ Uint16 *uni;
1296
+
1297
+ uni=sge_Latin1_Uni(string);
1298
+
1299
+ ret=sge_tt_textout_UNI(Surface,font,uni,x,y,fcolor,bcolor,Alpha);
1300
+ free(uni);
1301
+
1302
+ return ret;
1303
+ }
1304
+
1305
+ //==================================================================================
1306
+ // Renders the Latin-1 string to TrueType on surface, with the color fcolor.
1307
+ // bcolor is the target color for the antialiasing.
1308
+ // Alpha sets the transparency of the text (0-solid, 255-max). (RGB)
1309
+ //==================================================================================
1310
+ SDL_Rect sge_tt_textout(SDL_Surface *Surface, sge_TTFont *font, const char *string, Sint16 x, Sint16 y, Uint8 fR, Uint8 fG, Uint8 fB, Uint8 bR, Uint8 bG, Uint8 bB, int Alpha)
1311
+ {
1312
+ SDL_Rect ret;
1313
+ Uint16 *uni;
1314
+
1315
+ uni=sge_Latin1_Uni(string);
1316
+
1317
+ ret=sge_tt_textout_UNI(Surface,font,uni,x,y, fR,fG,fB, bR,bG,bB, Alpha);
1318
+ free(uni);
1319
+
1320
+ return ret;
1321
+ }
1322
+
1323
+
1324
+ //==================================================================================
1325
+ // Renders the UTF-8 string to TrueType on surface, with the color fcolor.
1326
+ // bcolor is the target color for the antialiasing.
1327
+ // Alpha sets the transparency of the text (0-solid, 255-max).
1328
+ //==================================================================================
1329
+ SDL_Rect sge_tt_textout_UTF8(SDL_Surface *Surface, sge_TTFont *font, const char *string, Sint16 x, Sint16 y, Uint32 fcolor, Uint32 bcolor, int Alpha)
1330
+ {
1331
+ SDL_Rect ret;
1332
+ Uint16 *uni;
1333
+
1334
+ uni=sge_UTF8_Uni(string);
1335
+
1336
+ ret=sge_tt_textout_UNI(Surface,font,uni,x,y,fcolor,bcolor,Alpha);
1337
+ free(uni);
1338
+
1339
+ return ret;
1340
+ }
1341
+
1342
+ //==================================================================================
1343
+ // Renders the UTF-8 string to TrueType on surface, with the color fcolor.
1344
+ // bcolor is the target color for the antialiasing.
1345
+ // Alpha sets the transparency of the text (0-solid, 255-max). (RGB)
1346
+ //==================================================================================
1347
+ SDL_Rect sge_tt_textout_UTF8(SDL_Surface *Surface, sge_TTFont *font, const char *string, Sint16 x, Sint16 y, Uint8 fR, Uint8 fG, Uint8 fB, Uint8 bR, Uint8 bG, Uint8 bB, int Alpha)
1348
+ {
1349
+ SDL_Rect ret;
1350
+ Uint16 *uni;
1351
+
1352
+ uni=sge_UTF8_Uni(string);
1353
+
1354
+ ret=sge_tt_textout_UNI(Surface,font,uni,x,y, fR,fG,fB, bR,bG,bB, Alpha);
1355
+ free(uni);
1356
+
1357
+ return ret;
1358
+ }
1359
+
1360
+
1361
+ //==================================================================================
1362
+ // Renders the formatet Latin-1 string to TrueType on surface, with the color fcolor.
1363
+ // bcolor is the target color for the antialiasing.
1364
+ // Alpha sets the transparency of the text (0-solid, 255-max). (RGB ONLY)
1365
+ // * just like printf(char *format,...) *
1366
+ //==================================================================================
1367
+ SDL_Rect sge_tt_textoutf(SDL_Surface *Surface, sge_TTFont *font, Sint16 x, Sint16 y, Uint8 fR, Uint8 fG, Uint8 fB, Uint8 bR, Uint8 bG, Uint8 bB, int Alpha ,char *format,...)
1368
+ {
1369
+ char buf[256];
1370
+
1371
+ va_list ap;
1372
+
1373
+ #ifdef __WIN32__
1374
+ va_start((va_list*)ap, format); //Stupid win32 crosscompiler
1375
+ #else
1376
+ va_start(ap, format);
1377
+ #endif
1378
+
1379
+ vsprintf(buf, format, ap);
1380
+ va_end(ap);
1381
+
1382
+ return sge_tt_textout(Surface, font, buf, x,y, fR,fG,fB, bR,bG,bB, Alpha);
1383
+ }
1384
+
1385
+
1386
+
1387
+
1388
+ /**********************************************************************************/
1389
+ /** TTF 'input' functions **/
1390
+ /**********************************************************************************/
1391
+
1392
+ // The old code that once lurked here has been replaced by shiny new code that uses
1393
+ // the text classes.
1394
+
1395
+ int sge_tt_input(SDL_Surface *screen, sge_TTFont *font, char *string, Uint8 flags,int pos, int len, Sint16 x,Sint16 y, Uint8 fR,Uint8 fG,Uint8 fB, Uint8 bR,Uint8 bG,Uint8 bB, int Alpha)
1396
+ {
1397
+ if( pos==0 && len>0 )
1398
+ string[0] = '\0';
1399
+
1400
+ sge_TextSurface text(screen, string, x, y-sge_TTF_FontAscent(font));
1401
+ text.set_ttFont(font, fR,fG,fB, bR, bG, bB);
1402
+ text.show_cursor(true);
1403
+ text.set_alpha(Alpha);
1404
+ text.max_chars(len-1);
1405
+
1406
+ int ret = sge_text_input(&text, flags);
1407
+
1408
+ strncpy( string, text.get_string(false).c_str(), sizeof(char)*len );
1409
+ return ret;
1410
+ }
1411
+
1412
+ int sge_tt_input_UNI(SDL_Surface *screen, sge_TTFont *font, Uint16 *string, Uint8 flags, int pos, int len, Sint16 x,Sint16 y, Uint8 fR,Uint8 fG,Uint8 fB, Uint8 bR,Uint8 bG,Uint8 bB, int Alpha)
1413
+ {
1414
+ sge_TextSurface text(screen, "", x, y-sge_TTF_FontAscent(font));
1415
+
1416
+ if( pos!=0 )
1417
+ text.change_uctext(string);
1418
+
1419
+ text.set_ttFont(font, fR,fG,fB, bR, bG, bB);
1420
+ text.show_cursor(true);
1421
+ text.set_alpha(Alpha);
1422
+ text.max_chars(len-1);
1423
+
1424
+ int ret = sge_text_input(&text, flags);
1425
+
1426
+ Uint16 *tmp = text.get_ucstring(false);
1427
+
1428
+ strncpy( (char*)string, (char*)tmp, sizeof(Uint16)*len );
1429
+
1430
+ delete[] tmp;
1431
+
1432
+ return ret;
1433
+ }
1434
+
1435
+ int sge_tt_input_UNI(SDL_Surface *screen, sge_TTFont *font, Uint16 *string, Uint8 flags, int pos,int len, Sint16 x,Sint16 y, Uint32 fcol,Uint32 bcol, int Alpha)
1436
+ {
1437
+ Uint8 fr,fg,fb, br,bg,bb;
1438
+
1439
+ SDL_GetRGB(fcol, screen->format, &fr, &fg, &fb);
1440
+ SDL_GetRGB(bcol, screen->format, &br, &bg, &bb);
1441
+
1442
+ return sge_tt_input_UNI(screen, font, string, flags, pos,len, x,y, fr,fg,fb, br,bg,bb, Alpha);
1443
+ }
1444
+
1445
+
1446
+ int sge_tt_input(SDL_Surface *screen, sge_TTFont *font, char *string, Uint8 flags, int pos,int len, Sint16 x,Sint16 y, Uint32 fcol,Uint32 bcol, int Alpha)
1447
+ {
1448
+ Uint8 fr,fg,fb, br,bg,bb;
1449
+
1450
+ SDL_GetRGB(fcol, screen->format, &fr, &fg, &fb);
1451
+ SDL_GetRGB(bcol, screen->format, &br, &bg, &bb);
1452
+
1453
+ return sge_tt_input(screen, font, string, flags, pos,len, x,y, fr,fg,fb, br,bg,bb, Alpha);
1454
+ }
1455
+
1456
+ #endif /* _SGE_NOTTF */