This repository has been archived by the owner on Feb 11, 2021. It is now read-only.
/
testsprite2.c
369 lines (337 loc) · 11.3 KB
1
2
3
/* Simple program: Move N sprites around on the screen as fast as possible */
#include <stdlib.h>
4
#include <stdio.h>
5
6
#include <time.h>
7
#include "common.h"
8
9
10
11
#define NUM_SPRITES 100
#define MAX_SPEED 1
12
static CommonState *state;
13
14
static int num_sprites;
static SDL_TextureID *sprites;
15
16
17
18
19
static SDL_bool cycle_color;
static SDL_bool cycle_alpha;
static int cycle_direction = 1;
static int current_alpha = 0;
static int current_color = 0;
20
21
22
static SDL_Rect *positions;
static SDL_Rect *velocities;
static int sprite_w, sprite_h;
23
static SDL_BlendMode blendMode = SDL_BLENDMODE_MASK;
24
static SDL_TextureScaleMode scaleMode = SDL_TEXTURESCALEMODE_NONE;
25
26
27
28
29
30
31
32
33
34
35
36
37
38
/* Call this instead of exit(), so we can clean up SDL: atexit() is evil. */
static void
quit(int rc)
{
if (sprites) {
SDL_free(sprites);
}
if (positions) {
SDL_free(positions);
}
if (velocities) {
SDL_free(velocities);
}
39
CommonQuit(state);
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
exit(rc);
}
int
LoadSprite(char *file)
{
int i;
SDL_Surface *temp;
/* Load the sprite image */
temp = SDL_LoadBMP(file);
if (temp == NULL) {
fprintf(stderr, "Couldn't load %s: %s", file, SDL_GetError());
return (-1);
}
sprite_w = temp->w;
sprite_h = temp->h;
/* Set transparent pixel as the pixel at (0,0) */
if (temp->format->palette) {
SDL_SetColorKey(temp, SDL_SRCCOLORKEY, *(Uint8 *) temp->pixels);
61
62
63
} else {
switch (temp->format->BitsPerPixel) {
case 15:
64
65
SDL_SetColorKey(temp, SDL_SRCCOLORKEY,
(*(Uint16 *) temp->pixels) & 0x00007FFF);
66
67
68
69
70
break;
case 16:
SDL_SetColorKey(temp, SDL_SRCCOLORKEY, *(Uint16 *) temp->pixels);
break;
case 24:
71
72
SDL_SetColorKey(temp, SDL_SRCCOLORKEY,
(*(Uint32 *) temp->pixels) & 0x00FFFFFF);
73
74
75
76
77
break;
case 32:
SDL_SetColorKey(temp, SDL_SRCCOLORKEY, *(Uint32 *) temp->pixels);
break;
}
78
79
80
}
/* Create textures from the image */
81
82
for (i = 0; i < state->num_windows; ++i) {
SDL_SelectRenderer(state->windows[i]);
83
sprites[i] = SDL_CreateTextureFromSurface(0, temp);
84
85
86
87
88
if (!sprites[i]) {
fprintf(stderr, "Couldn't create texture: %s\n", SDL_GetError());
SDL_FreeSurface(temp);
return (-1);
}
89
90
SDL_SetTextureBlendMode(sprites[i], blendMode);
SDL_SetTextureScaleMode(sprites[i], scaleMode);
91
92
93
94
95
96
97
98
99
100
101
102
}
SDL_FreeSurface(temp);
/* We're ready to roll. :) */
return (0);
}
void
MoveSprites(SDL_WindowID window, SDL_TextureID sprite)
{
int i, n;
int window_w, window_h;
103
SDL_Rect temp;
104
SDL_Rect *position, *velocity;
105
106
107
108
109
110
SDL_SelectRenderer(window);
/* Query the sizes */
SDL_GetWindowSize(window, &window_w, &window_h);
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
/* Cycle the color and alpha, if desired */
if (cycle_color) {
current_color += cycle_direction;
if (current_color < 0) {
current_color = 0;
cycle_direction = -cycle_direction;
}
if (current_color > 255) {
current_color = 255;
cycle_direction = -cycle_direction;
}
SDL_SetTextureColorMod(sprite, 255, (Uint8) current_color,
(Uint8) current_color);
}
if (cycle_alpha) {
current_alpha += cycle_direction;
if (current_alpha < 0) {
current_alpha = 0;
cycle_direction = -cycle_direction;
}
if (current_alpha > 255) {
current_alpha = 255;
cycle_direction = -cycle_direction;
}
SDL_SetTextureAlphaMod(sprite, (Uint8) current_alpha);
}
138
/* Draw a gray background */
139
140
SDL_SetRenderDrawColor(0xA0, 0xA0, 0xA0, 0xFF);
SDL_RenderFill(NULL);
141
142
/* Test points */
143
144
145
146
147
148
SDL_SetRenderDrawColor(0xFF, 0x00, 0x00, 0xFF);
SDL_RenderPoint(0, 0);
SDL_RenderPoint(window_w-1, 0);
SDL_RenderPoint(0, window_h-1);
SDL_RenderPoint(window_w-1, window_h-1);
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
/* Test horizontal and vertical lines */
SDL_SetRenderDrawColor(0x00, 0xFF, 0x00, 0xFF);
SDL_RenderLine(1, 0, window_w-2, 0);
SDL_RenderLine(1, window_h-1, window_w-2, window_h-1);
SDL_RenderLine(0, 1, 0, window_h-2);
SDL_RenderLine(window_w-1, 1, window_w-1, window_h-2);
/* Test fill */
SDL_SetRenderDrawColor(0xFF, 0xFF, 0xFF, 0xFF);
temp.x = window_w-sprite_w-1;
temp.y = 1;
temp.w = sprite_w;
temp.h = sprite_h;
SDL_RenderFill(&temp);
temp.x = 1;
temp.y = window_h-sprite_h-1;
temp.w = sprite_w;
temp.h = sprite_h;
SDL_RenderFill(&temp);
/* Test copy */
temp.x = 1;
temp.y = 1;
temp.w = sprite_w;
temp.h = sprite_h;
SDL_RenderCopy(sprite, NULL, &temp);
temp.x = window_w-sprite_w-1;
temp.y = window_h-sprite_h-1;
temp.w = sprite_w;
temp.h = sprite_h;
SDL_RenderCopy(sprite, NULL, &temp);
/* Test diagonal lines */
SDL_SetRenderDrawColor(0x00, 0xFF, 0x00, 0xFF);
SDL_RenderLine(sprite_w, sprite_h,
window_w-sprite_w-2, window_h-sprite_h-2);
SDL_RenderLine(window_w-sprite_w-2, sprite_h,
sprite_w, window_h-sprite_h-2);
188
189
/* Move the sprite, bounce at the wall, and draw */
n = 0;
190
191
192
193
194
195
196
197
198
for (i = 0; i < num_sprites; ++i) {
position = &positions[i];
velocity = &velocities[i];
position->x += velocity->x;
if ((position->x < 0) || (position->x >= (window_w - sprite_w))) {
velocity->x = -velocity->x;
position->x += velocity->x;
}
position->y += velocity->y;
199
if ((position->y < 0) || (position->y >= (window_h - sprite_h))) {
200
201
202
203
204
velocity->y = -velocity->y;
position->y += velocity->y;
}
/* Blit the sprite onto the screen */
205
SDL_RenderCopy(sprite, NULL, position);
206
207
208
209
210
211
212
213
214
215
216
217
218
}
/* Update the screen! */
SDL_RenderPresent();
}
int
main(int argc, char *argv[])
{
int i, done;
SDL_Event event;
Uint32 then, now, frames;
219
220
221
222
223
224
225
/* Initialize parameters */
num_sprites = NUM_SPRITES;
/* Initialize test framework */
state = CommonCreateState(argv, SDL_INIT_VIDEO);
if (!state) {
return 1;
226
}
227
228
for (i = 1; i < argc;) {
int consumed;
229
230
231
consumed = CommonArg(state, i);
if (consumed == 0) {
232
233
234
235
consumed = -1;
if (SDL_strcasecmp(argv[i], "--blend") == 0) {
if (argv[i + 1]) {
if (SDL_strcasecmp(argv[i + 1], "none") == 0) {
236
blendMode = SDL_BLENDMODE_NONE;
237
consumed = 2;
238
} else if (SDL_strcasecmp(argv[i + 1], "mask") == 0) {
239
blendMode = SDL_BLENDMODE_MASK;
240
consumed = 2;
241
} else if (SDL_strcasecmp(argv[i + 1], "blend") == 0) {
242
blendMode = SDL_BLENDMODE_BLEND;
243
244
consumed = 2;
} else if (SDL_strcasecmp(argv[i + 1], "add") == 0) {
245
blendMode = SDL_BLENDMODE_ADD;
246
247
consumed = 2;
} else if (SDL_strcasecmp(argv[i + 1], "mod") == 0) {
248
blendMode = SDL_BLENDMODE_MOD;
249
250
251
consumed = 2;
}
}
252
253
254
} else if (SDL_strcasecmp(argv[i], "--scale") == 0) {
if (argv[i + 1]) {
if (SDL_strcasecmp(argv[i + 1], "none") == 0) {
255
scaleMode = SDL_TEXTURESCALEMODE_NONE;
256
257
consumed = 2;
} else if (SDL_strcasecmp(argv[i + 1], "fast") == 0) {
258
scaleMode = SDL_TEXTURESCALEMODE_FAST;
259
260
consumed = 2;
} else if (SDL_strcasecmp(argv[i + 1], "slow") == 0) {
261
scaleMode = SDL_TEXTURESCALEMODE_SLOW;
262
263
consumed = 2;
} else if (SDL_strcasecmp(argv[i + 1], "best") == 0) {
264
scaleMode = SDL_TEXTURESCALEMODE_BEST;
265
266
267
consumed = 2;
}
}
268
269
270
271
272
273
} else if (SDL_strcasecmp(argv[i], "--cyclecolor") == 0) {
cycle_color = SDL_TRUE;
consumed = 1;
} else if (SDL_strcasecmp(argv[i], "--cyclealpha") == 0) {
cycle_alpha = SDL_TRUE;
consumed = 1;
274
275
276
277
} else if (SDL_isdigit(*argv[i])) {
num_sprites = SDL_atoi(argv[i]);
consumed = 1;
}
278
}
279
if (consumed < 0) {
280
fprintf(stderr,
281
"Usage: %s %s [--blend none|mask|blend|add|mod] [--scale none|fast|slow|best] [--cyclecolor] [--cyclealpha]\n",
282
argv[0], CommonUsage(state));
283
284
quit(1);
}
285
i += consumed;
286
}
287
288
if (!CommonInit(state)) {
quit(2);
289
290
291
}
/* Create the windows, initialize the renderers, and load the textures */
292
293
294
sprites =
(SDL_TextureID *) SDL_malloc(state->num_windows * sizeof(*sprites));
if (!sprites) {
295
296
297
fprintf(stderr, "Out of memory!\n");
quit(2);
}
298
299
for (i = 0; i < state->num_windows; ++i) {
SDL_SelectRenderer(state->windows[i]);
300
301
SDL_SetRenderDrawColor(0xA0, 0xA0, 0xA0, 0xFF);
SDL_RenderFill(NULL);
302
303
304
305
306
307
308
309
310
311
312
313
314
}
if (LoadSprite("icon.bmp") < 0) {
quit(2);
}
/* Allocate memory for the sprite info */
positions = (SDL_Rect *) SDL_malloc(num_sprites * sizeof(SDL_Rect));
velocities = (SDL_Rect *) SDL_malloc(num_sprites * sizeof(SDL_Rect));
if (!positions || !velocities) {
fprintf(stderr, "Out of memory!\n");
quit(2);
}
srand(time(NULL));
315
if (scaleMode != SDL_TEXTURESCALEMODE_NONE) {
316
317
318
sprite_w += sprite_w / 2;
sprite_h += sprite_h / 2;
}
319
for (i = 0; i < num_sprites; ++i) {
320
321
positions[i].x = rand() % (state->window_w - sprite_w);
positions[i].y = rand() % (state->window_h - sprite_h);
322
323
324
325
326
327
328
329
330
331
positions[i].w = sprite_w;
positions[i].h = sprite_h;
velocities[i].x = 0;
velocities[i].y = 0;
while (!velocities[i].x && !velocities[i].y) {
velocities[i].x = (rand() % (MAX_SPEED * 2 + 1)) - MAX_SPEED;
velocities[i].y = (rand() % (MAX_SPEED * 2 + 1)) - MAX_SPEED;
}
}
332
/* Main render loop */
333
334
335
336
337
338
339
frames = 0;
then = SDL_GetTicks();
done = 0;
while (!done) {
/* Check for events */
++frames;
while (SDL_PollEvent(&event)) {
340
CommonEvent(state, &event, &done);
341
342
343
344
345
switch (event.type) {
case SDL_WINDOWEVENT:
switch (event.window.event) {
case SDL_WINDOWEVENT_EXPOSED:
SDL_SelectRenderer(event.window.windowID);
346
347
SDL_SetRenderDrawColor(0xA0, 0xA0, 0xA0, 0xFF);
SDL_RenderFill(NULL);
348
349
350
351
352
353
354
break;
}
break;
default:
break;
}
}
355
356
for (i = 0; i < state->num_windows; ++i) {
MoveSprites(state->windows[i], sprites[i]);
357
358
359
360
361
362
}
}
/* Print out some timing information */
now = SDL_GetTicks();
if (now > then) {
363
double fps = ((double) frames * 1000) / (now - then);
364
printf("%2.2f frames per second\n", fps);
365
366
367
368
369
}
quit(0);
}
/* vi: set ts=4 sw=4 expandtab: */