Next phase of online keyconfig; editable names of templates, and

some other groundwork for the next steps.


git-svn-id: svn://svn.code.sf.net/p/sc2/code/trunk@2424 8092fc87-c524-0410-9efc-e669fe64eaf9
This commit is contained in:
mcmartin
2006-08-27 15:01:37 +00:00
parent b5d6c11bcd
commit e0366a964f
9 changed files with 268 additions and 53 deletions
+1
View File
@@ -1,4 +1,5 @@
Changes towards version 0.6: Changes towards version 0.6:
- Input templates can now be renamed, both online and off - Michael
- Fixed an integer-size error that was causing crashes on AMD64, from - Fixed an integer-size error that was causing crashes on AMD64, from
Solomon Peachy (#895) - Michael Solomon Peachy (#895) - Michael
- Added some generic lib code to be used by future code. - SvdB - Added some generic lib code to be used by future code. - SvdB
+61 -29
View File
@@ -9,6 +9,7 @@ Audio Options
Resources Options Resources Options
Controls Setup Controls Setup
Advanced Options Advanced Options
Edit Controls
#(CHOICES) #(CHOICES)
Resolution Resolution
@@ -31,6 +32,7 @@ Sound Quality
Slave Shields Slave Shields
Player One Player One
Player Two Player Two
Control Set
#(CAT_0_OPTS) #(CAT_0_OPTS)
320x240 320x240
@@ -304,81 +306,95 @@ Slave shields pulsate.
This mimics the 3do verion. This mimics the 3do verion.
#(CAT_18_OPTS) #(CAT_18_OPTS)
Keyboard #1 Placeholder
Keyboard #2 Placeholder
Keyboard #3 Placeholder
Joystick #1 Placeholder
Joystick #2 Placeholder
Joystick #3 Placeholder
#(CAT_18_OPT_0_DESC) #(CAT_18_OPT_0_DESC)
Player 1 uses the Keyboard 1 template.
Player 1 controls the bottom player in Player 1 controls the bottom player in
Super Melee, and the entire Full Game. Super Melee, and the entire Full Game.
#(CAT_18_OPT_1_DESC) #(CAT_18_OPT_1_DESC)
Player 1 uses the Keyboard 2 template.
Player 1 controls the bottom player in Player 1 controls the bottom player in
Super Melee, and the entire Full Game. Super Melee, and the entire Full Game.
#(CAT_18_OPT_2_DESC) #(CAT_18_OPT_2_DESC)
Player 1 uses the Keyboard 3 template.
Player 1 controls the bottom player in Player 1 controls the bottom player in
Super Melee, and the entire Full Game. Super Melee, and the entire Full Game.
#(CAT_18_OPT_3_DESC) #(CAT_18_OPT_3_DESC)
Player 1 uses the Joystick 1 template.
Player 1 controls the bottom player in Player 1 controls the bottom player in
Super Melee, and the entire Full Game. Super Melee, and the entire Full Game.
#(CAT_18_OPT_4_DESC) #(CAT_18_OPT_4_DESC)
Player 1 uses the Joystick 2 template.
Player 1 controls the bottom player in Player 1 controls the bottom player in
Super Melee, and the entire Full Game. Super Melee, and the entire Full Game.
#(CAT_18_OPT_5_DESC) #(CAT_18_OPT_5_DESC)
Player 1 uses the Joystick 3 template.
Player 1 controls the bottom player in Player 1 controls the bottom player in
Super Melee, and the entire Full Game. Super Melee, and the entire Full Game.
#(CAT_19_OPTS) #(CAT_19_OPTS)
Keyboard #1 Placeholder
Keyboard #2 Placeholder
Keyboard #3 Placeholder
Joystick #1 Placeholder
Joystick #2 Placeholder
Joystick #3 Placeholder
#(CAT_19_OPT_0_DESC) #(CAT_19_OPT_0_DESC)
Player 2 uses the Keyboard 1 template.
Player 2 controls the top player Player 2 controls the top player
in Super Melee. in Super Melee.
#(CAT_19_OPT_1_DESC) #(CAT_19_OPT_1_DESC)
Player 2 uses the Keyboard 2 template.
Player 2 controls the top player Player 2 controls the top player
in Super Melee. in Super Melee.
#(CAT_19_OPT_2_DESC) #(CAT_19_OPT_2_DESC)
Player 2 uses the Keyboard 3 template.
Player 2 controls the top player Player 2 controls the top player
in Super Melee. in Super Melee.
#(CAT_19_OPT_3_DESC) #(CAT_19_OPT_3_DESC)
Player 2 uses the Joystick 1 template.
Player 2 controls the top player Player 2 controls the top player
in Super Melee. in Super Melee.
#(CAT_19_OPT_4_DESC) #(CAT_19_OPT_4_DESC)
Player 2 uses the Joystick 2 template.
Player 2 controls the top player Player 2 controls the top player
in Super Melee. in Super Melee.
#(CAT_19_OPT_5_DESC) #(CAT_19_OPT_5_DESC)
Player 2 uses the Joystick 3 template.
Player 2 controls the top player Player 2 controls the top player
in Super Melee. in Super Melee.
#(CAT_20_OPTS)
Placeholder
Placeholder
Placeholder
Placeholder
Placeholder
Placeholder
#(CAT_20_OPT_0_DESC)
Select the control template to edit.
#(CAT_20_OPT_1_DESC)
Select the control template to edit.
#(CAT_20_OPT_2_DESC)
Select the control template to edit.
#(CAT_20_OPT_3_DESC)
Select the control template to edit.
#(CAT_20_OPT_4_DESC)
Select the control template to edit.
#(CAT_20_OPT_5_DESC)
Select the control template to edit.
#(SLIDERS) #(SLIDERS)
Music Volume Music Volume
SFX Volume SFX Volume
@@ -402,6 +418,8 @@ Sound Options
Resources Options Resources Options
Configure Controls Configure Controls
Advanced Options Advanced Options
Edit Controls
Back to Control Select
#(BUTTON_0_DESC) #(BUTTON_0_DESC)
Return to the main menu. Return to the main menu.
@@ -436,9 +454,16 @@ Currently partially implemented.
Select underlying drivers or other Select underlying drivers or other
hardware-dependent options. hardware-dependent options.
#(BUTTON_8_DESC)
Edit key control sets.
#(BUTTON_9_DESC)
Return to control set selection screen.
#(LABELS) #(LABELS)
Incomplete Incomplete
Keyconfig incomplete Keyconfig header
Editkey header
#(LABEL_0) #(LABEL_0)
This part of the configuration This part of the configuration
@@ -447,7 +472,14 @@ has not yet been implemented.
Expect it in a future version. Expect it in a future version.
#(LABEL_1) #(LABEL_1)
Control templates are currently defined To view or edit key controls,
in the KEYS.CFG file stored near your select the option below:
save games. A future UQM version will
offer in-game key configuration. #(LABEL_2)
Controls
#(TEXT_ENTRIES)
Name
#(TEXT_ENTRIES_INITIAL)
Placeholder
+1
View File
@@ -58,6 +58,7 @@ uio_DirList *availableAddons;
extern uio_Repository *repository; extern uio_Repository *repository;
extern uio_DirHandle *rootDir; extern uio_DirHandle *rootDir;
INPUT_TEMPLATE input_templates[6];
static const char *findFileInDirs (const char *locs[], int numLocs, static const char *findFileInDirs (const char *locs[], int numLocs,
const char *file); const char *file);
+13
View File
@@ -49,6 +49,19 @@ extern uio_DirHandle *meleeDir;
extern uio_DirList *availableAddons; extern uio_DirList *availableAddons;
/* These get edited by TEXTENTRY widgets, so they should have room to
* hold as much as one of them allows by default. */
typedef struct _input_template {
char name[30];
/* This should eventually also hold things like Joystick Port
* and whether or not joysticks are enabled at all, and
* possibly the whole configuration scheme. If we do that, we
* can actually ditch much of VControl. */
} INPUT_TEMPLATE;
extern INPUT_TEMPLATE input_templates[6];
void prepareContentDir (const char *contentDirName, const char **addons); void prepareContentDir (const char *contentDirName, const char **addons);
void prepareConfigDir (const char *configDirName); void prepareConfigDir (const char *configDirName);
void prepareMeleeDir (void); void prepareMeleeDir (void);
+7
View File
@@ -600,8 +600,15 @@ Widget_HandleEventChoice (WIDGET *_self, int event)
self->highlighted = 0; self->highlighted = 0;
return TRUE; return TRUE;
case WIDGET_EVENT_SELECT: case WIDGET_EVENT_SELECT:
{
int oldval = self->selected;
self->selected = self->highlighted; self->selected = self->highlighted;
if (self->onChange)
{
(*(self->onChange))(self, oldval);
}
return TRUE; return TRUE;
}
default: default:
return FALSE; return FALSE;
} }
+2
View File
@@ -74,6 +74,7 @@ typedef struct _widget_choice {
int maxcolumns; int maxcolumns;
CHOICE_OPTION *options; CHOICE_OPTION *options;
int selected, highlighted; int selected, highlighted;
void (*onChange)(struct _widget_choice *self, int oldval);
} WIDGET_CHOICE; } WIDGET_CHOICE;
typedef struct _widget_button { typedef struct _widget_button {
@@ -130,6 +131,7 @@ typedef struct _widget_textentry {
// handleEventSelect is an overridable callback event // handleEventSelect is an overridable callback event
// called by the default handleEvent implementation // called by the default handleEvent implementation
// can be NULL, in which case SELECT is ignored // can be NULL, in which case SELECT is ignored
void (*onChange)(struct _widget_textentry *self);
const char *category; const char *category;
char value[WIDGET_TEXTENTRY_WIDTH]; char value[WIDGET_TEXTENTRY_WIDTH];
int maxlen; int maxlen;
@@ -20,4 +20,3 @@
#include "inpintrn.h" #include "inpintrn.h"
volatile BOOLEAN ExitRequested, GamePaused; volatile BOOLEAN ExitRequested, GamePaused;
+123 -23
View File
@@ -58,6 +58,10 @@ static int do_engine (WIDGET *self, int event);
static int do_resources (WIDGET *self, int event); static int do_resources (WIDGET *self, int event);
static int do_keyconfig (WIDGET *self, int event); static int do_keyconfig (WIDGET *self, int event);
static int do_advanced (WIDGET *self, int event); static int do_advanced (WIDGET *self, int event);
static int do_editkeys (WIDGET *self, int event);
static void change_template (WIDGET_CHOICE *self, int oldval);
static void rename_template (WIDGET_TEXTENTRY *self);
#ifdef HAVE_OPENGL #ifdef HAVE_OPENGL
#define RES_OPTS 4 #define RES_OPTS 4
@@ -65,11 +69,11 @@ static int do_advanced (WIDGET *self, int event);
#define RES_OPTS 2 #define RES_OPTS 2
#endif #endif
#define MENU_COUNT 7 #define MENU_COUNT 8
#define CHOICE_COUNT 20 #define CHOICE_COUNT 21
#define SLIDER_COUNT 3 #define SLIDER_COUNT 3
#define BUTTON_COUNT 8 #define BUTTON_COUNT 10
#define LABEL_COUNT 2 #define LABEL_COUNT 3
#define TEXTENTRY_COUNT 1 #define TEXTENTRY_COUNT 1
/* The space for our widgets */ /* The space for our widgets */
@@ -85,23 +89,26 @@ static WIDGET_TEXTENTRY textentries[TEXTENTRY_COUNT];
typedef int (*HANDLER)(WIDGET *, int); typedef int (*HANDLER)(WIDGET *, int);
static int choice_widths[CHOICE_COUNT] = { static int choice_widths[CHOICE_COUNT] = {
3, 2, 3, 3, 2, 2, 2, 2, 2, 3, 2, 3, 3, 2, 2, 2, 2, 2, 2,
2, 2, 2, 3, 2, 2, 3, 3, 2, 2, 2, 3, 2, 2, 3, 3, 2, 3, 3,
3, 3 }; 3 };
static HANDLER button_handlers[BUTTON_COUNT] = { static HANDLER button_handlers[BUTTON_COUNT] = {
quit_main_menu, quit_sub_menu, do_graphics, do_engine, quit_main_menu, quit_sub_menu, do_graphics, do_engine,
do_audio, do_resources, do_keyconfig, do_advanced }; do_audio, do_resources, do_keyconfig, do_advanced, do_editkeys,
do_keyconfig };
static int menu_sizes[MENU_COUNT] = { static int menu_sizes[MENU_COUNT] = {
8, 5, 6, 9, 2, 4, 7, 5, 6, 9, 2, 5,
#ifdef HAVE_OPENGL #ifdef HAVE_OPENGL
5 }; 5,
#else #else
4 }; 4,
#endif #endif
4
};
static int menu_bgs[MENU_COUNT] = { 0, 1, 1, 2, 3, 1, 2 }; static int menu_bgs[MENU_COUNT] = { 0, 1, 1, 2, 3, 1, 2, 1 };
/* These refer to uninitialized widgets, but that's OK; we'll fill /* These refer to uninitialized widgets, but that's OK; we'll fill
* them in before we touch them */ * them in before we touch them */
@@ -112,7 +119,6 @@ static WIDGET *main_widgets[] = {
(WIDGET *)(&buttons[5]), (WIDGET *)(&buttons[5]),
(WIDGET *)(&buttons[6]), (WIDGET *)(&buttons[6]),
(WIDGET *)(&buttons[7]), (WIDGET *)(&buttons[7]),
(WIDGET *)(&textentries[0]),
(WIDGET *)(&buttons[0]) }; (WIDGET *)(&buttons[0]) };
static WIDGET *graphics_widgets[] = { static WIDGET *graphics_widgets[] = {
@@ -154,15 +160,22 @@ static WIDGET *keyconfig_widgets[] = {
(WIDGET *)(&choices[18]), (WIDGET *)(&choices[18]),
(WIDGET *)(&choices[19]), (WIDGET *)(&choices[19]),
(WIDGET *)(&labels[1]), (WIDGET *)(&labels[1]),
(WIDGET *)(&buttons[8]),
(WIDGET *)(&buttons[1]) }; (WIDGET *)(&buttons[1]) };
static WIDGET *editkeys_widgets[] = {
(WIDGET *)(&choices[20]),
(WIDGET *)(&labels[2]),
(WIDGET *)(&textentries[0]),
(WIDGET *)(&buttons[9]) };
static WIDGET *incomplete_widgets[] = { static WIDGET *incomplete_widgets[] = {
(WIDGET *)(&labels[0]), (WIDGET *)(&labels[0]),
(WIDGET *)(&buttons[1]) }; (WIDGET *)(&buttons[1]) };
static WIDGET **menu_widgets[MENU_COUNT] = { static WIDGET **menu_widgets[MENU_COUNT] = {
main_widgets, graphics_widgets, audio_widgets, engine_widgets, main_widgets, graphics_widgets, audio_widgets, engine_widgets,
incomplete_widgets, keyconfig_widgets, advanced_widgets }; incomplete_widgets, keyconfig_widgets, advanced_widgets, editkeys_widgets };
static int static int
quit_main_menu (WIDGET *self, int event) quit_main_menu (WIDGET *self, int event)
@@ -267,6 +280,39 @@ do_advanced (WIDGET *self, int event)
return FALSE; return FALSE;
} }
static int
do_editkeys (WIDGET *self, int event)
{
if (event == WIDGET_EVENT_SELECT)
{
next = (WIDGET *)(&menus[7]);
/* Prepare the components */
choices[20].selected = 0;
strncpy (textentries[0].value, input_templates[0].name, textentries[0].maxlen);
textentries[0].value[textentries[0].maxlen] = 0;
(*next->receiveFocus) (next, WIDGET_EVENT_DOWN);
return TRUE;
}
(void)self;
return FALSE;
}
static void
change_template (WIDGET_CHOICE *self, int oldval)
{
strncpy (textentries[0].value, input_templates[self->selected].name, WIDGET_TEXTENTRY_WIDTH);
textentries[0].value[WIDGET_TEXTENTRY_WIDTH-1] = 0;
}
static void
rename_template (WIDGET_TEXTENTRY *self)
{
strncpy (input_templates[choices[20].selected].name, self->value, WIDGET_TEXTENTRY_WIDTH);
/* TODO: This will have to change if the size of the input_templates name is changed */
input_templates[choices[20].selected].name[WIDGET_TEXTENTRY_WIDTH-1] = 0;
}
#define NUM_STEPS 20 #define NUM_STEPS 20
#define X_STEP (SCREEN_WIDTH / NUM_STEPS) #define X_STEP (SCREEN_WIDTH / NUM_STEPS)
#define Y_STEP (SCREEN_HEIGHT / NUM_STEPS) #define Y_STEP (SCREEN_HEIGHT / NUM_STEPS)
@@ -306,6 +352,7 @@ SetDefaults (void)
choices[17].selected = opts.shield; choices[17].selected = opts.shield;
choices[18].selected = opts.player1; choices[18].selected = opts.player1;
choices[19].selected = opts.player2; choices[19].selected = opts.player2;
choices[20].selected = 0;
sliders[0].value = opts.musicvol; sliders[0].value = opts.musicvol;
sliders[1].value = opts.sfxvol; sliders[1].value = opts.sfxvol;
@@ -474,6 +521,13 @@ OnTextEntryEvent (WIDGET_TEXTENTRY *widget)
{ // editing failed (canceled) -- revert the changes { // editing failed (canceled) -- revert the changes
utf8StringCopy (widget->value, widget->maxlen, revert_buf); utf8StringCopy (widget->value, widget->maxlen, revert_buf);
} }
else
{
if (widget->onChange)
{
(*(widget->onChange))(widget);
}
}
widget->state = WTE_NORMAL; widget->state = WTE_NORMAL;
redraw_menu (); redraw_menu ();
@@ -539,7 +593,6 @@ init_widgets (void)
/* Options */ /* Options */
if (SplitString (GetStringAddress (SetAbsStringTableIndex (SetupTab, 2)), '\n', 100, buffer, bank) != CHOICE_COUNT) if (SplitString (GetStringAddress (SetAbsStringTableIndex (SetupTab, 2)), '\n', 100, buffer, bank) != CHOICE_COUNT)
{ {
/* TODO: Ignore extras instead of dying. */
log_add (log_Fatal, "PANIC: Incorrect number of Choice Options"); log_add (log_Fatal, "PANIC: Incorrect number of Choice Options");
exit (EXIT_FAILURE); exit (EXIT_FAILURE);
} }
@@ -558,6 +611,7 @@ init_widgets (void)
choices[i].selected = 0; choices[i].selected = 0;
choices[i].highlighted = 0; choices[i].highlighted = 0;
choices[i].maxcolumns = choice_widths[i]; choices[i].maxcolumns = choice_widths[i];
choices[i].onChange = NULL;
} }
/* Fill in the options now */ /* Fill in the options now */
@@ -607,6 +661,17 @@ init_widgets (void)
/* The first choice is resolution, and is handled specially */ /* The first choice is resolution, and is handled specially */
choices[0].numopts = RES_OPTS; choices[0].numopts = RES_OPTS;
/* Choices 18-20 are also special, being the names of the key configurations */
for (i = 0; i < 6; i++)
{
choices[18].options[i].optname = input_templates[i].name;
choices[19].options[i].optname = input_templates[i].name;
choices[20].options[i].optname = input_templates[i].name;
}
/* Choice 20 has a special onChange handler, too. */
choices[20].onChange = change_template;
/* Sliders */ /* Sliders */
if (index >= count) if (index >= count)
{ {
@@ -755,14 +820,18 @@ init_widgets (void)
} }
} }
/* Check for garbage at the end */ /* Text Entry boxes */
if (index < count) if (index >= count)
{ {
log_add (log_Warning, "WARNING: Setup strings had %d garbage entries at the end.", log_add (log_Fatal, "PANIC: String table cut short while reading text entries");
count - index); exit (EXIT_FAILURE);
} }
/* Hardcode the test textentry for now. */ if (SplitString (GetStringAddress (SetAbsStringTableIndex (SetupTab, index++)), '\n', 100, buffer, bank) != TEXTENTRY_COUNT)
{
log_add (log_Fatal, "PANIC: Incorrect number of Text Entries");
exit (EXIT_FAILURE);
}
for (i = 0; i < TEXTENTRY_COUNT; i++) for (i = 0; i < TEXTENTRY_COUNT; i++)
{ {
textentries[i].parent = NULL; textentries[i].parent = NULL;
@@ -772,15 +841,38 @@ init_widgets (void)
textentries[i].height = Widget_HeightOneLine; textentries[i].height = Widget_HeightOneLine;
textentries[i].width = Widget_WidthFullScreen; textentries[i].width = Widget_WidthFullScreen;
textentries[i].handleEventSelect = OnTextEntryEvent; textentries[i].handleEventSelect = OnTextEntryEvent;
textentries[i].category = NULL; textentries[i].category = buffer[i];
textentries[i].value[0] = 0; textentries[i].value[0] = 0;
textentries[i].maxlen = WIDGET_TEXTENTRY_WIDTH-1; textentries[i].maxlen = WIDGET_TEXTENTRY_WIDTH-1;
textentries[i].state = WTE_NORMAL; textentries[i].state = WTE_NORMAL;
textentries[i].cursor_pos = 0; textentries[i].cursor_pos = 0;
} }
textentries[0].category = "TestText"; if (index >= count)
strcpy (textentries[0].value, "Sample value"); {
log_add (log_Fatal, "PANIC: String table cut short while reading text entries");
exit (EXIT_FAILURE);
}
if (SplitString (GetStringAddress (SetAbsStringTableIndex (SetupTab, index++)), '\n', 100, buffer, bank) != TEXTENTRY_COUNT)
{
/* TODO: Ignore extras instead of dying. */
log_add (log_Fatal, "PANIC: Incorrect number of Text Entries");
exit (EXIT_FAILURE);
}
for (i = 0; i < TEXTENTRY_COUNT; i++)
{
strncpy (textentries[i].value, buffer[i], textentries[i].maxlen);
textentries[i].value[textentries[i].maxlen] = 0;
}
textentries[0].onChange = rename_template;
/* Check for garbage at the end */
if (index < count)
{
log_add (log_Warning, "WARNING: Setup strings had %d garbage entries at the end.",
count - index);
}
} }
static void static void
@@ -1015,6 +1107,7 @@ SetGlobalOptions (GLOBALOPTS *opts)
int NewWidth = ScreenWidthActual; int NewWidth = ScreenWidthActual;
int NewHeight = ScreenHeightActual; int NewHeight = ScreenHeightActual;
int NewDriver = GraphicsDriver; int NewDriver = GraphicsDriver;
int i;
NewGfxFlags &= ~TFB_GFXFLAGS_SCALE_ANY; NewGfxFlags &= ~TFB_GFXFLAGS_SCALE_ANY;
@@ -1172,5 +1265,12 @@ SetGlobalOptions (GLOBALOPTS *opts)
SetMusicVolume (musicVolume); SetMusicVolume (musicVolume);
SetSpeechVolume (speechVolumeScale); SetSpeechVolume (speechVolumeScale);
res_PutString ("config.keys.1.name", input_templates[0].name);
res_PutString ("config.keys.2.name", input_templates[1].name);
res_PutString ("config.keys.3.name", input_templates[2].name);
res_PutString ("config.keys.4.name", input_templates[3].name);
res_PutString ("config.keys.5.name", input_templates[4].name);
res_PutString ("config.keys.6.name", input_templates[5].name);
res_SaveFilename (configDir, "uqm.cfg", "config."); res_SaveFilename (configDir, "uqm.cfg", "config.");
} }
+60
View File
@@ -354,6 +354,66 @@ main (int argc, char *argv[])
parseVolume (res_GetString ("config.speechvol"), parseVolume (res_GetString ("config.speechvol"),
&options.speechVolumeScale, "speech volume"); &options.speechVolumeScale, "speech volume");
} }
if (res_HasKey ("config.keys.1.name"))
{
strncpy(input_templates[0].name, res_GetString ("config.keys.1.name"), 30);
input_templates[0].name[29] = 0;
}
else
{
strcpy (input_templates[0].name, "Keyboard 1");
res_PutString ("config.keys.1.name", input_templates[0].name);
}
if (res_HasKey ("config.keys.2.name"))
{
strncpy(input_templates[1].name, res_GetString ("config.keys.2.name"), 30);
input_templates[1].name[29] = 0;
}
else
{
strcpy (input_templates[1].name, "Keyboard 2");
res_PutString ("config.keys.2.name", input_templates[1].name);
}
if (res_HasKey ("config.keys.3.name"))
{
strncpy(input_templates[2].name, res_GetString ("config.keys.3.name"), 30);
input_templates[2].name[29] = 0;
}
else
{
strcpy (input_templates[2].name, "Keyboard 3");
res_PutString ("config.keys.3.name", input_templates[2].name);
}
if (res_HasKey ("config.keys.4.name"))
{
strncpy(input_templates[3].name, res_GetString ("config.keys.4.name"), 30);
input_templates[3].name[29] = 0;
}
else
{
strcpy (input_templates[3].name, "Joystick 1");
res_PutString ("config.keys.4.name", input_templates[3].name);
}
if (res_HasKey ("config.keys.5.name"))
{
strncpy(input_templates[4].name, res_GetString ("config.keys.5.name"), 30);
input_templates[4].name[29] = 0;
}
else
{
strcpy (input_templates[4].name, "Joystick 2");
res_PutString ("config.keys.5.name", input_templates[4].name);
}
if (res_HasKey ("config.keys.6.name"))
{
strncpy(input_templates[5].name, res_GetString ("config.keys.6.name"), 30);
input_templates[5].name[29] = 0;
}
else
{
strcpy (input_templates[5].name, "Joystick 3");
res_PutString ("config.keys.6.name", input_templates[5].name);
}
optionsResult = parseOptions (argc, argv, &options); optionsResult = parseOptions (argc, argv, &options);
if (optionsResult != 0) if (optionsResult != 0)