- replaced YES/NO with true/false
[supertux.git] / src / text.cpp
1 //
2 // C Implementation: text
3 //
4 // Description:
5 //
6 //
7 // Author: Tobias Glaesser <tobi.web@gmx.de>, (C) 2004
8 //
9 // Copyright: See COPYING file that comes with this distribution
10 //
11 //
12
13 #include <stdlib.h>
14 #include <string.h>
15 #include "globals.h"
16 #include "defines.h"
17 #include "screen.h"
18 #include "text.h"
19
20 void text_load(text_type* ptext, const std::string& file, int kind, int w, int h)
21 {
22   int mx, my;
23   SDL_Surface *conv;
24   int pixels;
25   int i;
26   
27   if(kind == TEXT_TEXT)
28     {
29       mx = 26;
30       my = 3;
31     }
32   else if(kind == TEXT_NUM)
33     {
34       mx = 10;
35       my = 1;
36     }
37   else
38     {
39       mx = 0;
40       my = 0;
41     }
42   ptext->kind = kind;
43   ptext->w = w;
44   ptext->h = h;
45
46   texture_load(&ptext->chars, file, USE_ALPHA);
47
48   /* Load shadow font. */
49   conv = SDL_DisplayFormatAlpha(ptext->chars.sdl_surface);
50   pixels = conv->w * conv->h;
51   SDL_LockSurface(conv);
52   for(i = 0; i < pixels; ++i)
53     {
54       Uint32 *p = (Uint32 *)conv->pixels + i;
55       *p = *p & conv->format->Amask;
56     }
57   SDL_UnlockSurface(conv);
58   SDL_SetAlpha(conv, SDL_SRCALPHA, 128);
59   texture_from_sdl_surface(&ptext->shadow_chars,conv,USE_ALPHA);
60
61   SDL_FreeSurface(conv);
62 }
63
64 void text_draw(text_type* ptext,const  char* text, int x, int y, int shadowsize, int update)
65 {
66   if(text != NULL)
67     {
68       if(shadowsize != 0)
69         text_draw_chars(ptext,&ptext->shadow_chars, text,x+shadowsize,y+shadowsize, update);
70
71       text_draw_chars(ptext,&ptext->chars, text,x,y, update);
72     }
73 }
74
75 void text_draw_chars(text_type* ptext, texture_type* pchars,const  char* text, int x, int y, int update)
76 {
77   int i,j,len;
78   int w, h;
79
80   len = strlen(text);
81   w = ptext->w;
82   h = ptext->h;
83
84   if(ptext->kind == TEXT_TEXT)
85     {
86       for( i = 0, j = 0; i < len; ++i,++j)
87         {
88           if( text[i] >= 'A' && text[i] <= 'Z')
89             texture_draw_part(pchars, (int)(text[i] - 'A')*w, 0, x+(j*w), y, ptext->w, ptext->h, update);
90           else if( text[i] >= 'a' && text[i] <= 'z')
91             texture_draw_part(pchars, (int)(text[i] - 'a')*w, h, x+(j*w), y, ptext->w, ptext->h, update);
92           else if ( text[i] >= '!' && text[i] <= '9')
93             texture_draw_part(pchars, (int)(text[i] - '!')*w, h*2, x+(j*w), y, ptext->w, ptext->h, update);
94           else if ( text[i] == '?')
95             texture_draw_part(pchars, 25*w, h*2, x+(j*w), y, ptext->w, ptext->h, update);
96           else if ( text[i] == '\n')
97             {
98               y += ptext->h + 2;
99               j = 0;
100             }
101         }
102     }
103   else if(ptext->kind == TEXT_NUM)
104     {
105       for( i = 0, j = 0; i < len; ++i, ++j)
106         {
107           if ( text[i] >= '0' && text[i] <= '9')
108             texture_draw_part(pchars, (int)(text[i] - '0')*w, 0, x+(j*w), y, w, h, update);
109           else if ( text[i] == '\n')
110             {
111               y += ptext->h + 2;
112               j = 0;
113             }
114         }
115     }
116 }
117
118 void text_draw_align(text_type* ptext, const char* text, int x, int y,
119                      TextHAlign halign, TextVAlign valign, int shadowsize, int update)
120 {
121   if(text != NULL)
122     {
123       switch (halign)
124         {
125         case A_RIGHT:
126           x += -(strlen(text)*ptext->w);
127           break;
128         case A_HMIDDLE:
129           x += -((strlen(text)*ptext->w)/2);
130           break;
131         case A_LEFT:
132           // default
133           break;
134         }
135
136       switch (valign)
137         {
138         case A_BOTTOM:
139           y -= ptext->h;
140           break;
141           
142         case A_VMIDDLE:
143           y -= ptext->h/2;
144
145         case A_TOP:
146           // default
147           break;
148         }
149
150       text_draw(ptext, text, x, y, shadowsize, update);
151     }
152 }
153
154 void text_drawf(text_type* ptext,const  char* text, int x, int y, TextHAlign halign, TextVAlign valign, int shadowsize, int update)
155 {
156   if(text != NULL)
157     {
158       if(halign == A_RIGHT)  /* FIXME: this doesn't work correctly for strings with newlines.*/
159         x += screen->w - (strlen(text)*ptext->w);
160       else if(halign == A_HMIDDLE)
161         x += screen->w/2 - ((strlen(text)*ptext->w)/2);
162
163       if(valign == A_BOTTOM)
164         y += screen->h - ptext->h;
165       else if(valign == A_VMIDDLE)
166         y += screen->h/2 - ptext->h/2;
167
168       text_draw(ptext,text,x,y,shadowsize,update);
169     }
170 }
171
172 void text_free(text_type* ptext)
173 {
174   if(ptext->kind == TEXT_TEXT)
175     texture_free(&ptext->chars);
176   else if(ptext->kind == TEXT_NUM)
177     texture_free(&ptext->chars);
178 }
179
180 /* --- ERASE TEXT: --- */
181
182 void erasetext(text_type* ptext,const  char * text, int x, int y, texture_type * ptexture, int update, int shadowsize)
183 {
184   SDL_Rect dest;
185
186
187   dest.x = x;
188   dest.y = y;
189   dest.w = strlen(text) * ptext->w + shadowsize;
190   dest.h = ptext->h;
191
192   if (dest.w > screen->w)
193     dest.w = screen->w;
194
195   texture_draw_part(ptexture,dest.x,dest.y,dest.x,dest.y,dest.w,dest.h,update);
196
197   if (update == UPDATE)
198     update_rect(screen, dest.x, dest.y, dest.w, dest.h);
199 }
200
201
202 /* --- ERASE CENTERED TEXT: --- */
203
204 void erasecenteredtext(text_type* ptext,const  char * text, int y, texture_type * ptexture, int update, int shadowsize)
205 {
206   erasetext(ptext, text, screen->w / 2 - (strlen(text) * 8), y, ptexture, update, shadowsize);
207 }