/
hero.c
138 lines (109 loc) · 4.54 KB
/
hero.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
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
/* ****************************************************************************
*
* Adaption of Casey's Handmade Hero in C with SDL
*
* Author: Christian Hamm
* Date: 25.02.2015
*
*************************************************************************** */
#include "hero.h"
// Dynamic loading of functions
#ifdef HERO_DYNLOAD
//typedef void *(*_Hero_PlayTestSound)(Hero_AudioDef audio_def);
typedef void *(*_Hero_UpdateGameState)(Hero_GameState *game_state,
Hero_GameInput *game_input,
SDL_Surface *buffer,
Hero_AudioDef audio_def);
#endif
int main(int argc, char **argv) {
// Init stuff
//srand((unsigned int) time(NULL));
SDL_Init(SDL_INIT_VIDEO | SDL_INIT_AUDIO | SDL_INIT_GAMECONTROLLER);
Hero_PrintSDLVersion();
// Audio stuff
Hero_AudioDef audio_def = Hero_InitAudio();
// Create the window and renderer
SDL_Window *window = SDL_CreateWindow(
"Handmade Hero",
SDL_WINDOWPOS_UNDEFINED,
SDL_WINDOWPOS_UNDEFINED,
k_window_width, k_window_height,
SDL_WINDOW_RESIZABLE);
// Get the window surface, make a copy of it and update the window
SDL_Surface *source = SDL_GetWindowSurface(window);
g_backbuffer = SDL_ConvertSurfaceFormat(source, source->format->format, 0);
Hero_ResizeAndUpdateWindow(window, g_backbuffer, SDL_TRUE);
SDL_FreeSurface(source);
// Loop things
SDL_bool sound_is_playing = SDL_FALSE;
Uint32 frame_step = 0;
SDL_bool running = SDL_TRUE;
//SDL_SetCursor(Hero_InitSystemCursor(arrow));
//SDL_ShowCursor(SDL_ENABLE);
// Game Setup
_Hero_UpdateGameState Hero_UpdateGameState = NULL;
Hero_GameInput *game_input = SDL_malloc(sizeof(Hero_GameInput));
SDL_zerop(game_input);
Hero_GameState *game_state = SDL_malloc(sizeof(Hero_GameState));
SDL_zerop(game_state);
game_state->player_position.abs_tile_x = 3;
game_state->player_position.abs_tile_y = 3;
game_state->player_position.tile_rel_x = 5.0f;
game_state->player_position.tile_rel_y = 5.0f;
while (running) {
// Performance
Uint64 perf_freq = SDL_GetPerformanceFrequency();
Uint64 perf_counter_start = SDL_GetPerformanceCounter();
#ifdef HERO_DYNLOAD
// Load our library every n frames
if ((frame_step % 30) == 0 || Hero_UpdateGameState == NULL) {
SDL_UnloadObject(g_logic_lib);
//log_debug("reloading symbols");
g_logic_lib = SDL_LoadObject("libherologic.so");
Hero_UpdateGameState = SDL_LoadFunction(g_logic_lib,
"Hero_UpdateGameState");
}
#endif
// Actual game stuff
running = Hero_HandleEvents(game_input);
//SDL_GetMouseState(&g_mouse_position.x, &g_mouse_position.y);
SDL_assert(Hero_UpdateGameState);
Hero_UpdateGameState(game_state, game_input, g_backbuffer, audio_def);
Hero_ResizeAndUpdateWindow(window, g_backbuffer, SDL_FALSE);
// TODO: Sound
/*
Sint16 debug_tone_volume = 1000;
Hero_DebugPlayTestSineWave(audio_def, 440, debug_tone_volume);
Hero_DebugPlayTestSineWave(audio_def, 220, debug_tone_volume);
Hero_DebugPlayTestSineWave(audio_def, 880, debug_tone_volume);
*/
//Hero_DebugPlayTestSquareWave(audio_def);
/*
if (!sound_is_playing) {
SDL_PauseAudioDevice(g_audio_device, 0);
sound_is_playing = SDL_TRUE;
}*/
// Performance
Uint64 perf_counter_end = SDL_GetPerformanceCounter();
Uint64 perf_counter_elapsed = perf_counter_end - perf_counter_start;
double perf_per_frame = ((
(1000.0f * (double) perf_counter_elapsed) /
(double) perf_freq));
// Ensure we are at a constant framerate
double fps_padding_time = k_display_msmax - perf_per_frame;
// Save the value for movement speed adjustment
game_input->frame_dt = (float) fps_padding_time * 0.01f;
if (fps_padding_time > 0)
SDL_Delay((Uint32) fps_padding_time);
if ((frame_step % 30) == 0)
log_debug("Frame stats: %f ms, max %f ms, padding %f ms",
perf_per_frame, k_display_msmax, fps_padding_time);
frame_step++;
}
log_debug("Shutting down...");
if (g_game_controller != NULL)
SDL_GameControllerClose(g_game_controller);
SDL_DestroyWindow(window);
SDL_Quit();
return 0;
}