#include #include "def.h" #include "pilot.h" #include "log.h" #include "player.h" #define KEY_PRESS 1. #define KEY_RELEASE -1. // Keybind structure. typedef struct { char* name; // Keybinding name, taken from keybindNames[] KeybindType type; // type, defined in player.h. int key; // Key/axis/button event number. double reverse; // 1. if normal, -1 if reversed, only useful for joystick axis. } Keybind; static Keybind** player_input; // Contains the players keybindings. // Name of each keybinding. const char* keybindNames[] = { "accel", "left", "right" }; Pilot* player = NULL; // extern in pilot.h static double player_turn = 0.; // Turn velocity from input. static double player_acc = 0.; // Accel velocity from input. // Used in pilot.c // Basically uses keyboard input instead of AI input. void player_think(Pilot* player, const double dt) { player->solid->dir_vel = 0.; if(player_turn) player->solid->dir_vel -= player->ship->turn * player_turn; vect_pset(&player->solid->force, player->ship->thrust * player_acc, player->solid->dir); } // Initialization/exit functions (does not assign keys). void input_init(void) { Keybind* tmp; int i; for(i = 0; keybindNames[i]; i++); // Get number of bindings. player_input = (Keybind**)malloc(i*sizeof(Keybind*)); // Create a null keybinding for each. for(i = 0; keybindNames[i]; i++) { tmp = MALLOC_L(Keybind); tmp->name = (char*)keybindNames[i]; tmp->type = KEYBIND_NULL; tmp->key = 0; tmp->reverse = 1.; player_input[i] = tmp; } } void input_exit(void) { int i; for(i = 0; keybindNames[i]; i++) free(player_input[i]); free(player_input); } // Binds key of type [type] to action keybind. void input_setKeybind(char* keybind, KeybindType type, int key, int reverse) { int i; for(i = 0; keybindNames[i]; i++) { if(strcmp(keybind, player_input[i]->name)==0) { player_input[i]->type = type; player_input[i]->key = key; player_input[i]->reverse = reverse ? -1. : 1.; return; } } } // == Run input method. ================================================ // keynum : Index of the player_input keybind. // value : Value of keypress (defined above). // abs : Whether or not it's an abs value (For those pesky joysticks. // ===================================================================== static void input_key(int keynum, double value, int abs) { if(strcmp(player_input[keynum]->name, "accel")==0) { if(abs)player_acc = value; else player_acc += value; } else if(strcmp(player_input[keynum]->name, "left")==0) { if(abs)player_turn = -value; else player_turn -= value; } else if(strcmp(player_input[keynum]->name, "right")==0) { if(abs) player_turn = value; else player_turn += value; } //Make sure values are sane. player_acc = ABS(player_acc); if(player_acc > 1.) player_acc = 1.; if(player_turn > 1.) player_turn = 1.; else if(player_turn < -1.) player_turn = -1.; } // --Events-- static void input_joyaxis(int axis, int value); static void input_joydown(int button); static void input_joyup(int button); static void input_keydown(SDLKey key); static void input_keyup(SDLKey key); // Joystick. // Axis. static void input_joyaxis(int axis, int value) { int i; for(i = 0; keybindNames[i]; i++) if(player_input[i]->type == KEYBIND_JAXIS && player_input[i]->key == axis) { input_key(i, -(player_input[i]->reverse) * (double)value / 32767., 1); return; } } // Joystick button down. static void input_joydown(int button) { int i; for(i = 0; keybindNames[i]; i++) if(player_input[i]->type == KEYBIND_JBUTTON && player_input[i]->key == button) { input_key(i, KEY_RELEASE, 0); return; } } // Joystick button up. static void input_joyup(int button) { int i; for(i = 0; keybindNames[i]; i++) if(player_input[i]->type == KEYBIND_JBUTTON && player_input[i]->key == button) { input_key(i, KEY_RELEASE, 0); return; } } // Keyboard. // Key down. static void input_keydown(SDLKey key) { int i; for(i = 0; keybindNames[i]; i++) if(player_input[i]->type == KEYBIND_KEYBOARD && player_input[i]->key == key) { input_key(i, KEY_PRESS, 0); return; } // Fire Escape. SDL_Event quit; if(key == SDLK_ESCAPE) { quit.type = SDL_QUIT; SDL_PushEvent(&quit); } } // Key up. static void input_keyup(SDLKey key) { int i; for(i = 0; keybindNames[i]; i++) if(player_input[i]->type == KEYBIND_KEYBOARD && player_input[i]->key == key) { input_key(i, KEY_RELEASE, 0); return; } } // Global input. // Just seperates the event types. void input_handle(SDL_Event* event) { switch(event->type) { case SDL_JOYAXISMOTION: input_joyaxis(event->jaxis.axis, event->jaxis.value); break; case SDL_JOYBUTTONDOWN: input_joydown(event->jbutton.button); break; case SDL_JOYBUTTONUP: input_joyup(event->jbutton.button); case SDL_KEYDOWN: input_keydown(event->key.keysym.sym); break; case SDL_KEYUP: input_keyup(event->key.keysym.sym); break; } }