From d49064dde0298aef4f9bd0b2d79000c215006564 Mon Sep 17 00:00:00 2001
From: Allanis <allanis@saracraft.net>
Date: Sat, 15 Mar 2014 20:26:40 +0000
Subject: [PATCH] [Add] Alright, you are now able to check up on the
 keybindings via options menu.

---
 src/input.c   | 10 ++++-----
 src/input.h   |  2 +-
 src/menu.c    | 12 ++++++-----
 src/options.c | 60 +++++++++++++++++++++++++++++++++++++++++++++++++--
 4 files changed, 71 insertions(+), 13 deletions(-)

diff --git a/src/input.c b/src/input.c
index b30bbaa..11a16b7 100644
--- a/src/input.c
+++ b/src/input.c
@@ -52,6 +52,7 @@ const char* keybindNames[] = {
   "end" /* Must terminate at the end. */
 };
 
+/* Keybinding descriptions. Should match in position of the names. */
 const char* keybindDescription[] = {
   /* Movement. */
   "Makes your ship accelerate forward.",
@@ -109,7 +110,7 @@ extern double player_turn;
 void input_setDefault(void) {
   /* Movement. */
   input_setKeybind("accel",           KEYBIND_KEYBOARD, SDLK_w,           KMOD_ALL,   0);
-  input_setKeybind("afterburn",       KEYBIND_KEYBOARD, SDLK_UNKNOWN,     KMOD_ALL,   0);
+  input_setKeybind("afterburn",       KEYBIND_NULL,     SDLK_UNKNOWN,     KMOD_ALL,   0);
   input_setKeybind("left",            KEYBIND_KEYBOARD, SDLK_a,           KMOD_ALL,   0);
   input_setKeybind("right",           KEYBIND_KEYBOARD, SDLK_d,           KMOD_ALL,   0);
   input_setKeybind("reverse",         KEYBIND_KEYBOARD, SDLK_s,           KMOD_ALL,   0);
@@ -208,11 +209,10 @@ void input_setKeybind(char* keybind, KeybindType type, int key,
   WARN("Unable to set keybind '%s', That command does not exist.", keybind);
 }
 
-/* @fn int input_getKeybind(char* keybind, KeybindType* type, int* reverse)
- *
+/**
  * @brief Get the value of a keybind.
  */
-int input_getKeybind(char* keybind, KeybindType* type, SDLMod* mod, int* reverse) {
+SDLKey input_getKeybind(char* keybind, KeybindType* type, SDLMod* mod, int* reverse) {
   int i;
   for(i = 0; strcmp(keybindNames[i], "end"); i++)
     if(strcmp(keybind, input_keybinds[i]->name)==0) {
@@ -223,7 +223,7 @@ int input_getKeybind(char* keybind, KeybindType* type, SDLMod* mod, int* reverse
     }
 
   WARN("Unable to get keybinding '%s', that command doesn't exist", keybind);
-  return -1;
+  return (SDLKey)-1;
 }
 
 /**
diff --git a/src/input.h b/src/input.h
index 9e3db67..ae6f282 100644
--- a/src/input.h
+++ b/src/input.h
@@ -14,7 +14,7 @@ typedef enum {
 /* Set input. */
 void input_setDefault(void);
 void input_setKeybind(char* keybind, KeybindType type, int key, SDLMod mod, int reverse);
-int  input_getKeybind(char* keybind, KeybindType* type, SDLMod* mod,  int* reverse);
+SDLKey input_getKeybind(char* keybind, KeybindType* type, SDLMod* mod,  int* reverse);
 const char* input_getKeybindDescription(char* keybind);
 
 /* Handle the events. */
diff --git a/src/menu.c b/src/menu.c
index 04347a7..90eeed0 100644
--- a/src/menu.c
+++ b/src/menu.c
@@ -21,6 +21,7 @@
 #include "rng.h"
 #include "nebulae.h"
 #include "pause.h"
+#include "options.h"
 #include "menu.h"
 
 #define MAIN_WIDTH          130   /**< Main menu width. */
@@ -43,8 +44,9 @@
 
 #define DEATH_WIDTH         130   /**< Death menu width. */
 #define DEATH_HEIGHT        150   /**< Death menu height. */
-#define OPTIONS_WIDTH       130   /**< Options menu width. */
-#define OPTIONS_HEIGHT      150   /**< Options menu height. */
+
+#define OPTIONS_WIDTH       249   /**< Options menu width. */
+#define OPTIONS_HEIGHT       90   /**< Options menu height. */
 
 #define BUTTON_WIDTH        90    /**< Button width, standard across menus. */
 #define BUTTON_HEIGHT       30    /**< Button height, standard across menus. */
@@ -640,11 +642,11 @@ void menu_options(void) {
   unsigned int wid;
 
   wid = window_create("Options", -1, -1, OPTIONS_WIDTH, OPTIONS_HEIGHT);
-  window_addButton(wid, 20, 20, BUTTON_WIDTH, BUTTON_HEIGHT,
+  window_addButton(wid, -20, 20, BUTTON_WIDTH, BUTTON_HEIGHT,
       "btnClose", "Close", menu_options_close);
-  window_addButton(wid, 20, 20+(BUTTON_HEIGHT+20),
+  window_addButton(wid, -20 - (BUTTON_WIDTH+20), 20,
       BUTTON_WIDTH, BUTTON_HEIGHT,
-      "btnKeybinds", "Keybindings", NULL);
+      "btnKeybinds", "Keybindings", (void(*)(unsigned int,char*))opt_menuKeybinds);
   menu_Open(MENU_OPTIONS);
 }
 
diff --git a/src/options.c b/src/options.c
index 0fe7c55..facc8d4 100644
--- a/src/options.c
+++ b/src/options.c
@@ -22,6 +22,7 @@
 /* Extern. */
 extern const char* keybindNames[];
 
+static const char* modToText(SDLMod mod);
 static void menuKeybinds_update(unsigned int wid, char* name);
 
 /**
@@ -57,16 +58,71 @@ void opt_menuKeybinds(void) {
 }
 
 /**
- *
+ * @brief Gets the human readable version of mod.
+ */
+static const char* modToText(SDLMod mod) {
+  switch(mod) {
+    case KMOD_LCTRL:    return "lctrl";
+    case KMOD_RCTRL:    return "rctrl";
+    case KMOD_LSHIFT:   return "lshift";
+    case KMOD_RSHIFT:   return "rshift";
+    case KMOD_LALT:     return "lalt";
+    case KMOD_RALT:     return "ralt";
+    case KMOD_LMETA:    return "lmeta";
+    case KMOD_RMETA:    return "rmeta";
+    case KMOD_ALL:      return "any";
+    default:            return "unknown";
+  }
+}
+
+/**
+ * @brief Updates the keybindings menu.
  */
 static void menuKeybinds_update(unsigned int wid, char* name) {
   (void) name;
   char* keybind;
   const char* desc;
 
+  SDLKey key;
+  KeybindType type;
+  SDLMod mod;
+  int reverse;
+  char buf[1024];
+  char pre[32];
+  char bind[32];
+
+  /* Get the keybind. */
   keybind = toolkit_getList(wid, "lstKeybinds");
   window_modifyText(wid, "txtName", keybind);
+
+  /* Get information. */
   desc = input_getKeybindDescription(keybind);
-  window_modifyText(wid, "txtDesc", (char*)desc);
+  key = input_getKeybind(keybind, &type, &mod, &reverse);
+
+  /* Create the text. */
+  switch(type) {
+    case KEYBIND_NULL:
+      snprintf(bind, 64, "Not bound");
+      break;
+    case KEYBIND_KEYBOARD:
+      snprintf(pre, 32, "keyboard:  %s%s",
+          (mod != KMOD_NONE) ? modToText(mod) : "",
+          (mod != KMOD_NONE) ? " + " : "");
+
+      /* Is key. */
+      if(isalnum(key))
+        snprintf(bind, 32, "%s%c", pre, (char)key);
+      else
+        snprintf(bind, 32, "%s<%d>", pre, key);
+      break;
+    case KEYBIND_JAXIS:
+      snprintf(bind, 64, "joy axis:   <%d>%s", key, (reverse) ? " rev" : "");
+      break;
+    case KEYBIND_JBUTTON:
+      snprintf(bind, 64, "joy button:   <%d>", key);
+      break;
+  }
+  snprintf(buf, 1024, "%s\n\n%s\n", desc, bind);
+  window_modifyText(wid, "txtDesc", buf);
 }