Mirai's Miscellaneous Misadventures
M15 / engines / sdl2.c
1
2
3
4#include <stdlib.h>
5#include <SDL2/SDL.h>
6
7#include "../mimimi.h"
8
9struct mirai_sdl2
10{
11 SDL_Renderer *renderer;
12 struct mirai_image *images;
13 SDL_Texture **textures;
14};
15
16static void mirai_sdl2_stamp(void *opaque, int x, int y, struct mirai_image *image)
17{
18 struct mirai_sdl2 *data = opaque;
19 SDL_Renderer *renderer = data->renderer;
20
21 SDL_Rect rect;
22 rect.x = x;
23 rect.y = y;
24 rect.w = image->width;
25 rect.h = image->height;
26
27 int i = image - data->images;
28
29 SDL_RenderCopy(renderer, data->textures[i], NULL, &rect);
30}
31
32int main(int argc, char **argv)
33{
34 atexit(&SDL_Quit);
35
36 SDL_Init(SDL_INIT_VIDEO);
37
38 SDL_Window *window;
39 SDL_Renderer *renderer;
40
41 SDL_CreateWindowAndRenderer(mirai_width, mirai_height, 0, &window, &renderer);
42 SDL_RenderSetLogicalSize(renderer, mirai_width, mirai_height);
43 SDL_SetWindowTitle(window, "Mirai's Miscellaneous Misadventures");
44
45 struct mirai_image *images = mirai_assets();
46 struct mirai_image *image = images;
47 int image_count = 0;
48
49 while (image->width != 0)
50 {
51 image_count++;
52 image++;
53 }
54 image = images;
55
56 SDL_Texture **textures = malloc(image_count * sizeof *textures);
57
58 for (int i = 0 ; image->width != 0 ; i++)
59 {
60 SDL_Surface *surface = SDL_CreateRGBSurface(0, image->width, image->height, 32, 0xFF000000, 0x00FF0000, 0x0000FF00, 0x000000FF);
61 for (int x = 0 ; x < image->width ; x++)
62 for (int y = 0 ; y < image->height ; y++)
63 {
64 static unsigned char xterm[] = {0x00, 0x5F, 0x87, 0xAF, 0xD7, 0xFF};
65
66 Uint32 o = x * 4 + y * surface->pitch;
67 Uint32 *pixel = (Uint32 *) ((char *) surface->pixels + o);
68
69 Uint32 r, g, b, a;
70 unsigned char color = image->colors[x + y * image->width];
71 if (color == 0)
72 {
73 r = 0x00;
74 g = 0x00;
75 b = 0x00;
76 a = 0x00;
77 }
78 else
79 {
80 color -= 16;
81 r = xterm[(color / 36) % 6];
82 g = xterm[(color / 6) % 6];
83 b = xterm[color % 6];
84 a = 0xFF;
85 }
86
87 *pixel = (r << 24) | (g << 16) | (b << 8) | (a << 0);
88 }
89
90 textures[i] = SDL_CreateTextureFromSurface(renderer, surface);
91
92 SDL_FreeSurface(surface);
93 image++;
94 }
95
96 struct mirai_sdl2 data = {renderer, images, textures};
97
98 struct mirai_engine engine = {&data, &mirai_sdl2_stamp};
99 struct mirai_game *game = malloc(mirai_game_size);
100 mirai_start(game, &engine);
101
102 Uint32 past = SDL_GetTicks();
103
104 for (;;)
105 {
106 Uint32 current = SDL_GetTicks();
107 Uint32 delay = current - past;
108 past = current;
109 if (delay < 33) SDL_Delay(33 - delay);
110
111 SDL_Event event;
112 while (SDL_PollEvent(&event))
113 {
114 if (event.type == SDL_QUIT) return 0;
115
116 if (event.type == SDL_KEYDOWN)
117 {
118 switch (event.key.keysym.sym)
119 {
120 default: continue;
121 case SDLK_q: return 0;
122 }
123 }
124 }
125
126 struct mirai_keys keys = {0, 0};
127
128 unsigned char *keyboard = SDL_GetKeyboardState(NULL);
129 if (keyboard[SDL_SCANCODE_LEFT]) keys.left = 1;
130 if (keyboard[SDL_SCANCODE_RIGHT]) keys.right = 1;
131
132 SDL_Rect rect = {0, 0, mirai_width, mirai_height};
133 SDL_SetRenderDrawColor(renderer, 0x00, 0x00, 0x00, 0xFF);
134 SDL_RenderClear(renderer);
135 SDL_SetRenderDrawColor(renderer, 0xEE, 0xEE, 0xEE, 0xFF);
136 SDL_RenderFillRect(renderer, &rect);
137 mirai_step(game, keys);
138 SDL_RenderPresent(renderer);
139 }
140}