5 * Copyright (C) 2003, 2007 Thomas Perl <thp@perli.net>
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation; either version 2
10 * of the License, or (at your option) any later version.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
33 static SDL_Surface
*buffer
;
35 static Uint32 fading_start
= 0;
37 static const char* filenames
[] = {
49 static const char* smallish_font_chars
= " !\"#----()'+,-./0123456789:;<=>?@abcdefghijklmnopqrstuvwxyz";
51 void init_graphics( const char *data_dir
) {
55 char temp
[MAXPATHLEN
];
58 strcpy( temp
, data_dir
);
59 strcat( temp
, "icon.png");
60 tmp
= IMG_Load( temp
);
62 SDL_WM_SetIcon( tmp
, NULL
);
63 SDL_FreeSurface( tmp
);
67 images
= (Image
*)calloc( GR_COUNT
, sizeof( Image
));
69 for( i
=0; i
<GR_COUNT
; i
++) {
70 strcpy( temp
, data_dir
);
71 strcat( temp
, filenames
[i
]);
72 tmp
= IMG_Load( temp
);
74 fprintf( stderr
, "Error: %s\n", SDL_GetError());
78 SDL_SetColorKey( tmp
, SDL_SRCCOLORKEY
, SDL_MapRGB( tmp
->format
, 0, 0, 0));
79 data
= SDL_DisplayFormatAlpha( tmp
);
80 SDL_FreeSurface( tmp
);
83 fprintf( stderr
, "Error: %s\n", SDL_GetError());
86 images
[i
].data
= data
;
89 buffer
= SDL_CreateRGBSurface( SDL_HWSURFACE
, WIDTH
, HEIGHT
, screen
->format
->BitsPerPixel
, screen
->format
->Rmask
, screen
->format
->Gmask
, screen
->format
->Bmask
, screen
->format
->Amask
);
92 fprintf( stderr
, "Cannot create buffer surface: %s\n", SDL_GetError());
96 void uninit_graphics() {
99 for( i
=0; i
<GR_COUNT
; i
++) {
100 SDL_FreeSurface( images
[i
].data
);
103 if( buffer
!= NULL
) {
104 SDL_FreeSurface( buffer
);
110 void show_sprite( unsigned int id
, int pos
, int items
, int x_offset
, int y_offset
, int opacity
) {
114 bitmap
= images
[id
].data
;
118 SDL_SetAlpha( bitmap
, SDL_SRCALPHA
| SDL_RLEACCEL
, opacity
);
120 dst
.w
= src
.w
= bitmap
->w
/items
;
121 dst
.h
= src
.h
= bitmap
->h
;
127 SDL_BlitSurface( bitmap
, &src
, screen
, &dst
);
130 void line_horiz( int y
, Uint8 r
, Uint8 g
, Uint8 b
) {
131 Uint32 color
= SDL_MapRGB( screen
->format
, r
, g
, b
);
139 SDL_FillRect( screen
, &rect
, color
);
142 void line_vert( int x
, Uint8 r
, Uint8 g
, Uint8 b
) {
143 Uint32 color
= SDL_MapRGB( screen
->format
, r
, g
, b
);
151 SDL_FillRect( screen
, &rect
, color
);
154 void rectangle( int x
, int y
, int w
, int h
, Uint8 r
, Uint8 g
, Uint8 b
) {
155 Uint32 color
= SDL_MapRGB( screen
->format
, r
, g
, b
);
163 SDL_FillRect( screen
, &rect
, color
);
166 void show_image( unsigned int id
, int x_offset
, int y_offset
, int opacity
) {
167 show_sprite( id
, 0, 1, x_offset
, y_offset
, opacity
);
170 void show_digit( int zahl
, int x_offset
, int y_offset
, int opacity
) {
171 show_sprite( GR_SCORE
, zahl
, 11, x_offset
, y_offset
, opacity
);
174 void introimage( unsigned int id
) {
177 for( i
=0; i
<256; i
+=10) {
179 show_image( id
, 0, 0, i
);
187 for( i
=255; i
>=0; i
-=10) {
189 show_image( id
, 0, 0, i
);
205 SDL_FillRect( screen
, &rect
, SDL_MapRGB( screen
->format
, 0, 0, 0));
209 int ticks
= SDL_GetTicks();
211 if( ticks
< fading_start
+FADE_DURATION
) {
212 SDL_SetAlpha( buffer
, SDL_SRCALPHA
| SDL_RLEACCEL
, 255-255*(ticks
-fading_start
)/FADE_DURATION
);
213 SDL_BlitSurface( buffer
, NULL
, screen
, NULL
);
216 SDL_UpdateRect( screen
, 0, 0, 0, 0);
221 SDL_BlitSurface( screen
, NULL
, buffer
, NULL
);
222 fading_start
= SDL_GetTicks();
226 return SDL_GetTicks() < fading_start
+FADE_DURATION
;
229 int font_get_metrics( unsigned int id
, char ch
, int* xp
, int* wp
) {
231 SDL_PixelFormat
*fmt
;
232 int pos
, x
= -1, w
= 0;
233 int search_pos
= 0, search_x
= 0;
234 Uint8 red
, green
, blue
;
237 if( id
> GR_COUNT
) return 0;
244 for( pos
= 0; pos
< strlen( smallish_font_chars
); pos
++) {
245 if( smallish_font_chars
[pos
] == ch
)
249 if( pos
== strlen( smallish_font_chars
)) {
253 bitmap
= images
[id
].data
;
254 fmt
= bitmap
->format
;
256 SDL_LockSurface( bitmap
);
257 while( search_x
< bitmap
->w
) {
258 pixel
= *( (Uint32
*)(bitmap
->pixels
+ search_x
*fmt
->BytesPerPixel
));
259 red
= (Uint8
)(((pixel
& fmt
->Rmask
) >> fmt
->Rshift
) << fmt
->Rloss
);
260 green
= (Uint8
)(((pixel
& fmt
->Gmask
) >> fmt
->Gshift
) << fmt
->Gloss
);
261 blue
= (Uint8
)(((pixel
& fmt
->Bmask
) >> fmt
->Bshift
) << fmt
->Bloss
);
263 /* Increase pos counter if we have a "marker" pixel (255,0,255) */
264 if( red
== 255 && green
== 0 && blue
== 255) {
266 if( search_pos
== pos
) {
268 } else if( search_pos
== pos
+ 1) {
276 SDL_UnlockSurface( bitmap
);
279 if( wp
!= NULL
) (*wp
) = w
;
280 if( xp
!= NULL
) (*xp
) = x
;
285 int font_draw_char( unsigned int id
, char ch
, int x_offset
, int y_offset
) {
290 font_get_metrics( id
, ch
, &x
, &w
);
291 if( x
== -1) return w
;
293 bitmap
= images
[id
].data
;
296 dst
.h
= src
.h
= bitmap
->h
- 1;
302 SDL_BlitSurface( bitmap
, &src
, screen
, &dst
);
307 void font_draw_string( unsigned int id
, char* s
, int x_offset
, int y_offset
, int start
, int animation
) {
312 if( animation
& ANIMATION_SPACING
) {
313 xw
= (int)fabsf((15.0*sinf( start
/10.0 + x_offset
/30.0)));
317 if( animation
& ANIMATION_SKIP_TWO
) {
318 x
-= (strlen(s
)*(int)(2.0*sinf( start
/ 10.0)))/2;
321 for( i
=0; i
<strlen(s
); i
++) {
322 if( animation
& ANIMATION_WAVE
) {
323 y
= y_offset
+ (int)(3.0*sinf( start
/10.0 + x
/30.0));
325 x
+= font_draw_char( id
, s
[i
], x
, y
);
326 if( animation
& ANIMATION_SKIP_TWO
) {
327 x
+= (int)(2.0*sinf( start
/ 10.0));
329 if( animation
& ANIMATION_SPACING
) {
330 x
+= (int)(xw
/strlen(s
));
335 int font_get_string_width( unsigned int id
, char* s
) {
338 for( i
=0; i
<strlen(s
); i
++) {
339 w
+= font_get_metrics( id
, s
[i
], NULL
, NULL
);