mirror of
https://github.com/ddnet/ddnet.git
synced 2024-11-10 01:58:19 +00:00
cleaned up the console code. added the ability to tune the game in runtime.
This commit is contained in:
parent
307c2cfae8
commit
1fe3202f0b
|
@ -142,6 +142,7 @@ nethash = CHash(
|
|||
"src/game/generated/nethash.c",
|
||||
"src/engine/e_protocol.h",
|
||||
"src/game/g_protocol.h",
|
||||
"src/game/g_tuning.h",
|
||||
"src/game/g_game.cpp", networkdata.header)
|
||||
|
||||
client_link_other = {}
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
#include <engine/e_packer.h>
|
||||
#include <engine/e_memheap.h>
|
||||
#include <engine/e_datafile.h>
|
||||
#include <engine/e_console.h>
|
||||
|
||||
#include <mastersrv/mastersrv.h>
|
||||
|
||||
|
@ -1207,20 +1208,49 @@ static void client_run()
|
|||
snd_shutdown();
|
||||
}
|
||||
|
||||
static void connect_command(void *result, void *user_data)
|
||||
{
|
||||
const char *address;
|
||||
console_result_string(result, 1, &address);
|
||||
client_connect(address);
|
||||
}
|
||||
|
||||
static void disconnect_command(void *result, void *user_data)
|
||||
{
|
||||
client_disconnect();
|
||||
}
|
||||
|
||||
static void quit_command(void *result, void *user_data)
|
||||
{
|
||||
client_quit();
|
||||
}
|
||||
|
||||
static void client_register_commands()
|
||||
{
|
||||
MACRO_REGISTER_COMMAND("quit", "", quit_command, 0x0);
|
||||
MACRO_REGISTER_COMMAND("connect", "s", connect_command, 0x0);
|
||||
MACRO_REGISTER_COMMAND("disconnect", "", disconnect_command, 0x0);
|
||||
}
|
||||
|
||||
int editor_main(int argc, char **argv);
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
/* preinit the mod */
|
||||
modc_preinit();
|
||||
|
||||
/* init the engine */
|
||||
dbg_msg("client", "starting...");
|
||||
engine_init("Teewars", argc, argv);
|
||||
engine_init("Teewars");
|
||||
|
||||
/* register all console commands */
|
||||
client_register_commands();
|
||||
modc_console_init();
|
||||
|
||||
/* parse the command line arguments */
|
||||
engine_parse_arguments(argc, argv);
|
||||
|
||||
/* run the client*/
|
||||
client_run();
|
||||
|
||||
|
||||
/* write down the config and quit */
|
||||
engine_writeconfig();
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -23,10 +23,10 @@ void config_reset();
|
|||
void config_load(const char *filename);
|
||||
void config_save(const char *filename);
|
||||
|
||||
typedef int (*config_int_getter)(CONFIGURATION *c);
|
||||
typedef const char *(*config_str_getter)(CONFIGURATION *c);
|
||||
typedef void (*config_int_setter)(CONFIGURATION *c, int val);
|
||||
typedef void (*config_str_setter)(CONFIGURATION *c, const char *str);
|
||||
typedef int (*CONFIG_INT_GETTER)(CONFIGURATION *c);
|
||||
typedef const char *(*CONFIG_STR_GETTER)(CONFIGURATION *c);
|
||||
typedef void (*CONFIG_INT_SETTER)(CONFIGURATION *c, int val);
|
||||
typedef void (*CONFIG_STR_SETTER)(CONFIGURATION *c, const char *str);
|
||||
|
||||
#define MACRO_CONFIG_INT(name,def,min,max) int config_get_ ## name (CONFIGURATION *c);
|
||||
#define MACRO_CONFIG_STR(name,len,def) const char *config_get_ ## name (CONFIGURATION *c);
|
||||
|
|
|
@ -1,9 +1,37 @@
|
|||
#include "e_system.h"
|
||||
#include "e_console.h"
|
||||
#include "e_config.h"
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
|
||||
#define CONSOLE_MAX_STR_LENGTH 255
|
||||
/* the maximum number of tokens occurs in a string of length CONSOLE_MAX_STR_LENGTH with tokens size 1 separated by single spaces */
|
||||
#define MAX_TOKENS (CONSOLE_MAX_STR_LENGTH+1)/2
|
||||
|
||||
enum
|
||||
{
|
||||
TOKEN_INT,
|
||||
TOKEN_FLOAT,
|
||||
TOKEN_STRING
|
||||
};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
int type;
|
||||
const char *stored_string;
|
||||
} TOKEN;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
char string_storage[CONSOLE_MAX_STR_LENGTH+1];
|
||||
char *next_string;
|
||||
|
||||
TOKEN tokens[MAX_TOKENS];
|
||||
unsigned int num_tokens;
|
||||
} LEXER_RESULT;
|
||||
|
||||
enum
|
||||
{
|
||||
STATE_START,
|
||||
|
@ -15,7 +43,7 @@ enum
|
|||
STATE_ESCAPE
|
||||
};
|
||||
|
||||
static const char *store_string(struct lexer_result *res, const char *str, int len)
|
||||
static const char *store_string(LEXER_RESULT *res, const char *str, int len)
|
||||
{
|
||||
const char *ptr = res->next_string;
|
||||
int escaped = 0;
|
||||
|
@ -48,10 +76,10 @@ static const char *store_string(struct lexer_result *res, const char *str, int l
|
|||
return ptr;
|
||||
}
|
||||
|
||||
static void save_token(struct lexer_result *res, int *index, const char **start, const char *end, int *state, int type)
|
||||
static void save_token(LEXER_RESULT *res, int *index, const char **start, const char *end, int *state, int type)
|
||||
{
|
||||
/* printf("Saving token with length %d\n", end - *start); */
|
||||
struct token *tok = &res->tokens[*index];
|
||||
TOKEN *tok = &res->tokens[*index];
|
||||
tok->stored_string = store_string(res, *start, end - *start);
|
||||
tok->type = type;
|
||||
++res->num_tokens;
|
||||
|
@ -66,14 +94,14 @@ static int digit(char c)
|
|||
return '0' <= c && c <= '9';
|
||||
}
|
||||
|
||||
static int lex(const char *line, struct lexer_result *res)
|
||||
static int lex(const char *line, LEXER_RESULT *res)
|
||||
{
|
||||
int state = STATE_START, i = 0;
|
||||
int length_left = CONSOLE_MAX_STR_LENGTH;
|
||||
const char *start, *c;
|
||||
res->num_tokens = 0;
|
||||
|
||||
memset(res, 0, sizeof(*res));
|
||||
mem_zero(res, sizeof(*res));
|
||||
res->next_string = res->string_storage;
|
||||
|
||||
for (c = start = line; *c != '\0' && res->num_tokens < MAX_TOKENS && length_left; ++c, --length_left)
|
||||
|
@ -170,33 +198,35 @@ static int lex(const char *line, struct lexer_result *res)
|
|||
return 0;
|
||||
}
|
||||
|
||||
int extract_result_string(struct lexer_result *result, int index, const char **str)
|
||||
int console_result_string(void *res, int index, const char **str)
|
||||
{
|
||||
LEXER_RESULT *result = (LEXER_RESULT *)res;
|
||||
|
||||
if (index < 0 || index >= result->num_tokens)
|
||||
return -1;
|
||||
else
|
||||
{
|
||||
struct token *t = &result->tokens[index];
|
||||
|
||||
TOKEN *t = &result->tokens[index];
|
||||
*str = t->stored_string;
|
||||
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
int extract_result_int(struct lexer_result *result, int index, int *i)
|
||||
int console_result_int(void *res, int index, int *i)
|
||||
{
|
||||
LEXER_RESULT *result = (LEXER_RESULT *)res;
|
||||
|
||||
if (index < 0 || index >= result->num_tokens)
|
||||
return -1;
|
||||
else
|
||||
{
|
||||
struct token *t = &result->tokens[index];
|
||||
TOKEN *t = &result->tokens[index];
|
||||
const char *str;
|
||||
|
||||
if (t->type != TOKEN_INT)
|
||||
return -2;
|
||||
|
||||
extract_result_string(result, index, &str);
|
||||
console_result_string(result, index, &str);
|
||||
|
||||
*i = atoi(str);
|
||||
|
||||
|
@ -204,19 +234,21 @@ int extract_result_int(struct lexer_result *result, int index, int *i)
|
|||
}
|
||||
}
|
||||
|
||||
int extract_result_float(struct lexer_result *result, int index, float *f)
|
||||
int console_result_float(void *res, int index, float *f)
|
||||
{
|
||||
LEXER_RESULT *result = (LEXER_RESULT *)res;
|
||||
|
||||
if (index < 0 || index >= result->num_tokens)
|
||||
return -1;
|
||||
else
|
||||
{
|
||||
struct token *t = &result->tokens[index];
|
||||
TOKEN *t = &result->tokens[index];
|
||||
const char *str;
|
||||
|
||||
if (t->type != TOKEN_INT && t->type != TOKEN_FLOAT)
|
||||
return -2;
|
||||
|
||||
extract_result_string(result, index, &str);
|
||||
console_result_string(result, index, &str);
|
||||
|
||||
*f = atof(str);
|
||||
|
||||
|
@ -243,7 +275,7 @@ void console_register(COMMAND *cmd)
|
|||
}
|
||||
|
||||
|
||||
static int console_validate(COMMAND *command, struct lexer_result *result)
|
||||
static int console_validate(COMMAND *command, LEXER_RESULT *result)
|
||||
{
|
||||
const char *c = command->params;
|
||||
int i = 1;
|
||||
|
@ -257,15 +289,15 @@ static int console_validate(COMMAND *command, struct lexer_result *result)
|
|||
switch (*c)
|
||||
{
|
||||
case 's':
|
||||
if (extract_result_string(result, i, &dummy_s))
|
||||
if (console_result_string(result, i, &dummy_s))
|
||||
return -1;
|
||||
break;
|
||||
case 'i':
|
||||
if (extract_result_int(result, i, &dummy_i))
|
||||
if (console_result_int(result, i, &dummy_i))
|
||||
return -1;
|
||||
break;
|
||||
case 'f':
|
||||
if (extract_result_float(result, i, &dummy_f))
|
||||
if (console_result_float(result, i, &dummy_f))
|
||||
return -1;
|
||||
break;
|
||||
default:
|
||||
|
@ -296,7 +328,7 @@ void console_print(const char *str)
|
|||
|
||||
void console_execute(const char *str)
|
||||
{
|
||||
struct lexer_result result;
|
||||
LEXER_RESULT result;
|
||||
int error;
|
||||
|
||||
if ((error = lex(str, &result)))
|
||||
|
@ -305,7 +337,7 @@ void console_execute(const char *str)
|
|||
{
|
||||
const char *name;
|
||||
COMMAND *command;
|
||||
extract_result_string(&result, 0, &name);
|
||||
console_result_string(&result, 0, &name);
|
||||
|
||||
command = console_find_command(name);
|
||||
|
||||
|
@ -329,33 +361,32 @@ void console_execute(const char *str)
|
|||
}
|
||||
}
|
||||
|
||||
static void echo_command(struct lexer_result *result, void *user_data)
|
||||
static void echo_command(void *result, void *user_data)
|
||||
{
|
||||
const char *str;
|
||||
extract_result_string(result, 1, &str);
|
||||
|
||||
console_result_string(result, 1, &str);
|
||||
console_print(str);
|
||||
}
|
||||
|
||||
|
||||
struct int_variable_data
|
||||
typedef struct
|
||||
{
|
||||
config_int_getter getter;
|
||||
config_int_setter setter;
|
||||
};
|
||||
CONFIG_INT_GETTER getter;
|
||||
CONFIG_INT_SETTER setter;
|
||||
} INT_VARIABLE_DATA;
|
||||
|
||||
struct str_variable_data
|
||||
typedef struct
|
||||
{
|
||||
config_str_getter getter;
|
||||
config_str_setter setter;
|
||||
};
|
||||
CONFIG_STR_GETTER getter;
|
||||
CONFIG_STR_SETTER setter;
|
||||
} STR_VARIABLE_DATA;
|
||||
|
||||
static void int_variable_command(struct lexer_result *result, void *user_data)
|
||||
static void int_variable_command(void *result, void *user_data)
|
||||
{
|
||||
struct int_variable_data *data = (struct int_variable_data *)user_data;
|
||||
INT_VARIABLE_DATA *data = (INT_VARIABLE_DATA *)user_data;
|
||||
int new_val;
|
||||
|
||||
if (extract_result_int(result, 1, &new_val))
|
||||
if (console_result_int(result, 1, &new_val))
|
||||
{
|
||||
char buf[256];
|
||||
sprintf(buf, "Value: %d", data->getter(&config));
|
||||
|
@ -367,12 +398,12 @@ static void int_variable_command(struct lexer_result *result, void *user_data)
|
|||
}
|
||||
}
|
||||
|
||||
static void str_variable_command(struct lexer_result *result, void *user_data)
|
||||
static void str_variable_command(void *result, void *user_data)
|
||||
{
|
||||
struct str_variable_data *data = (struct str_variable_data *)user_data;
|
||||
STR_VARIABLE_DATA *data = (STR_VARIABLE_DATA *)user_data;
|
||||
const char *new_val;
|
||||
|
||||
if (extract_result_string(result, 1, &new_val))
|
||||
if (console_result_string(result, 1, &new_val))
|
||||
{
|
||||
char buf[256];
|
||||
sprintf(buf, "Value: %s", data->getter(&config));
|
||||
|
@ -388,8 +419,8 @@ void console_init()
|
|||
{
|
||||
MACRO_REGISTER_COMMAND("echo", "s", echo_command, 0x0);
|
||||
|
||||
#define MACRO_CONFIG_INT(name,def,min,max) { static struct int_variable_data data = { &config_get_ ## name, &config_set_ ## name }; MACRO_REGISTER_COMMAND(#name, "?i", int_variable_command, &data) }
|
||||
#define MACRO_CONFIG_STR(name,len,def) { static struct str_variable_data data = { &config_get_ ## name, &config_set_ ## name }; MACRO_REGISTER_COMMAND(#name, "?s", str_variable_command, &data) }
|
||||
#define MACRO_CONFIG_INT(name,def,min,max) { static INT_VARIABLE_DATA data = { &config_get_ ## name, &config_set_ ## name }; MACRO_REGISTER_COMMAND(#name, "?i", int_variable_command, &data) }
|
||||
#define MACRO_CONFIG_STR(name,len,def) { static STR_VARIABLE_DATA data = { &config_get_ ## name, &config_set_ ## name }; MACRO_REGISTER_COMMAND(#name, "?s", str_variable_command, &data) }
|
||||
|
||||
#include "e_config_variables.h"
|
||||
|
||||
|
|
|
@ -5,46 +5,15 @@
|
|||
extern "C"{
|
||||
#endif
|
||||
|
||||
#define CONSOLE_MAX_STR_LENGTH 255
|
||||
/* the maximum number of tokens occurs in a string of length CONSOLE_MAX_STR_LENGTH with tokens size 1 separated by single spaces */
|
||||
#define MAX_TOKENS (CONSOLE_MAX_STR_LENGTH+1)/2
|
||||
|
||||
enum
|
||||
{
|
||||
TOKEN_INT,
|
||||
TOKEN_FLOAT,
|
||||
TOKEN_STRING
|
||||
};
|
||||
|
||||
struct token
|
||||
{
|
||||
int type;
|
||||
const char *stored_string;
|
||||
};
|
||||
|
||||
struct lexer_result
|
||||
{
|
||||
char string_storage[CONSOLE_MAX_STR_LENGTH+1];
|
||||
char *next_string;
|
||||
typedef void (*CONSOLE_CALLBACK)(void *result, void *user_data);
|
||||
|
||||
struct token tokens[MAX_TOKENS];
|
||||
unsigned int num_tokens;
|
||||
};
|
||||
|
||||
int extract_result_string(struct lexer_result *result, int index, const char **str);
|
||||
int extract_result_int(struct lexer_result *result, int index, int *i);
|
||||
int extract_result_float(struct lexer_result *result, int index, float *f);
|
||||
|
||||
typedef void (*console_callback)(struct lexer_result *result, void *user_data);
|
||||
|
||||
typedef struct COMMAND
|
||||
typedef struct COMMAND_t
|
||||
{
|
||||
const char *name;
|
||||
const char *params;
|
||||
console_callback callback;
|
||||
CONSOLE_CALLBACK callback;
|
||||
void *user_data;
|
||||
struct COMMAND *next;
|
||||
|
||||
struct COMMAND_t *next;
|
||||
} COMMAND;
|
||||
|
||||
void console_init();
|
||||
|
@ -53,6 +22,10 @@ void console_execute(const char *str);
|
|||
void console_print(const char *str);
|
||||
void console_register_print_callback(void (*callback)(const char *));
|
||||
|
||||
int console_result_string(void *result, int index, const char **str);
|
||||
int console_result_int(void *result, int index, int *i);
|
||||
int console_result_float(void *result, int index, float *f);
|
||||
|
||||
#define MACRO_REGISTER_COMMAND(name, params, func, ptr) { static COMMAND cmd = { name, params, func, ptr, 0x0 }; console_register(&cmd); }
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
|
|
@ -47,28 +47,29 @@ void engine_init(const char *appname, int argc, char **argv)
|
|||
|
||||
/* reset the config */
|
||||
config_reset();
|
||||
|
||||
/* load the configuration */
|
||||
{
|
||||
int i;
|
||||
int abs = 0;
|
||||
const char *config_filename = "default.cfg";
|
||||
char buf[1024];
|
||||
for(i = 1; i < argc; i++)
|
||||
{
|
||||
if(argv[i][0] == '-' && argv[i][1] == 'f' && argv[i][2] == 0 && argc - i > 1)
|
||||
{
|
||||
config_filename = argv[i+1];
|
||||
abs = 1;
|
||||
i++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(abs)
|
||||
config_load(config_filename);
|
||||
else
|
||||
config_load(engine_savepath(config_filename, buf, sizeof(buf)));
|
||||
void engine_parse_arguments(int argc, char **argv)
|
||||
{
|
||||
/* load the configuration */
|
||||
int i;
|
||||
int abs = 0;
|
||||
const char *config_filename = "default.cfg";
|
||||
char buf[1024];
|
||||
for(i = 1; i < argc; i++)
|
||||
{
|
||||
if(argv[i][0] == '-' && argv[i][1] == 'f' && argv[i][2] == 0 && argc - i > 1)
|
||||
{
|
||||
config_filename = argv[i+1];
|
||||
abs = 1;
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
||||
if(abs)
|
||||
config_load(config_filename);
|
||||
else
|
||||
config_load(engine_savepath(config_filename, buf, sizeof(buf)));
|
||||
|
||||
/* search arguments for overrides */
|
||||
{
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
/* copyright (c) 2007 magnus auvinen, see licence.txt for more info */
|
||||
|
||||
const char *engine_savepath(const char *filename, char *buffer, int max);
|
||||
void engine_init(const char *appname, int argc, char **argv);
|
||||
void engine_init(const char *appname);
|
||||
void engine_parse_arguments(int argc, char **argv);
|
||||
void engine_writeconfig();
|
||||
|
|
|
@ -6,10 +6,10 @@
|
|||
Section: Client Hooks
|
||||
*********************************************************************************/
|
||||
/*
|
||||
Function: modc_preinit
|
||||
Function: modc_console_init
|
||||
TODO
|
||||
*/
|
||||
void modc_preinit();
|
||||
void modc_console_init();
|
||||
|
||||
/*
|
||||
Function: modc_init
|
||||
|
|
|
@ -5,6 +5,11 @@
|
|||
/**********************************************************************************
|
||||
Section: Server Hooks
|
||||
**********************************************************************************/
|
||||
/*
|
||||
Function: mods_console_init
|
||||
TODO
|
||||
*/
|
||||
void mods_console_init();
|
||||
|
||||
/*
|
||||
Function: mods_init
|
||||
|
|
|
@ -11,6 +11,8 @@ extern "C" {
|
|||
#include "e_if_msg.h"
|
||||
#include "e_if_mods.h"
|
||||
|
||||
#include "e_console.h" /* TODO: clean this up*/
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -70,7 +70,7 @@ int snapstorage_get(SNAPSTORAGE *ss, int tick, int64 *tagtime, SNAPSHOT **data);
|
|||
|
||||
enum
|
||||
{
|
||||
SNAPBUILD_MAX_ITEMS = 512
|
||||
SNAPBUILD_MAX_ITEMS = 1024*2
|
||||
};
|
||||
|
||||
typedef struct SNAPBUILD
|
||||
|
|
|
@ -161,8 +161,7 @@ typedef struct IOINTERNAL *IOHANDLE;
|
|||
|
||||
/****
|
||||
Function: io_open
|
||||
|
||||
Opens a file.
|
||||
Opens a file.
|
||||
|
||||
Parameters:
|
||||
filename - File to open.
|
||||
|
@ -176,8 +175,7 @@ IOHANDLE io_open(const char *filename, int flags);
|
|||
|
||||
/****
|
||||
Function: io_read
|
||||
|
||||
Reads data into a buffer from a file.
|
||||
Reads data into a buffer from a file.
|
||||
|
||||
Parameters:
|
||||
io - Handle to the file to read data from.
|
||||
|
@ -192,8 +190,7 @@ unsigned io_read(IOHANDLE io, void *buffer, unsigned size);
|
|||
|
||||
/*****
|
||||
Function: io_skip
|
||||
|
||||
Skips data in a file.
|
||||
Skips data in a file.
|
||||
|
||||
Parameters:
|
||||
io - Handle to the file.
|
||||
|
@ -221,8 +218,7 @@ unsigned io_write(IOHANDLE io, const void *buffer, unsigned size);
|
|||
|
||||
/*****
|
||||
Function: io_seek
|
||||
|
||||
Seeks to a specified offset in the file.
|
||||
Seeks to a specified offset in the file.
|
||||
|
||||
Parameters:
|
||||
io - Handle to the file.
|
||||
|
@ -236,8 +232,7 @@ int io_seek(IOHANDLE io, int offset, int origin);
|
|||
|
||||
/*****
|
||||
Function: io_tell
|
||||
|
||||
Gets the current position in the file.
|
||||
Gets the current position in the file.
|
||||
|
||||
Parameters:
|
||||
io - Handle to the file.
|
||||
|
@ -249,8 +244,7 @@ long int io_tell(IOHANDLE io);
|
|||
|
||||
/*****
|
||||
Function: io_length
|
||||
|
||||
Gets the total length of the file. Resetting cursor to the beginning
|
||||
Gets the total length of the file. Resetting cursor to the beginning
|
||||
|
||||
Parameters:
|
||||
io - Handle to the file.
|
||||
|
@ -262,8 +256,7 @@ long int io_length(IOHANDLE io);
|
|||
|
||||
/*****
|
||||
Function: io_close
|
||||
|
||||
Closes a file.
|
||||
Closes a file.
|
||||
|
||||
Parameters:
|
||||
io - Handle to the file.
|
||||
|
|
|
@ -225,6 +225,9 @@ void server_setbrowseinfo(int game_type, int progression)
|
|||
|
||||
void server_kick(int client_id, const char *reason)
|
||||
{
|
||||
if(client_id < 0 || client_id > MAX_CLIENTS)
|
||||
return;
|
||||
|
||||
if(clients[client_id].state != SRVCLIENT_STATE_EMPTY)
|
||||
netserver_drop(net, client_id, reason);
|
||||
}
|
||||
|
@ -647,7 +650,7 @@ static void server_process_client_packet(NETPACKET *packet)
|
|||
if(config.rcon_password[0] != 0 && strcmp(pw, config.rcon_password) == 0)
|
||||
{
|
||||
dbg_msg("server", "cid=%d rcon='%s'", cid, cmd);
|
||||
config_set(cmd);
|
||||
console_execute(cmd);
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -1039,11 +1042,26 @@ static int server_run()
|
|||
return 0;
|
||||
}
|
||||
|
||||
static void server_register_commands()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
/* init the engine */
|
||||
dbg_msg("server", "starting...");
|
||||
engine_init("Teewars", argc, argv);
|
||||
engine_init("Teewars");
|
||||
|
||||
/* register all console commands */
|
||||
server_register_commands();
|
||||
mods_console_init();
|
||||
|
||||
/* parse the command line arguments */
|
||||
engine_parse_arguments(argc, argv);
|
||||
|
||||
/* run the server */
|
||||
server_run();
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -35,6 +35,7 @@ bool menu_active = false;
|
|||
bool menu_game_active = false;
|
||||
static bool emoticon_selector_active = false;
|
||||
|
||||
tuning_params tuning;
|
||||
|
||||
vec2 mouse_pos;
|
||||
vec2 local_character_pos;
|
||||
|
@ -1439,14 +1440,6 @@ void render_game()
|
|||
}
|
||||
}
|
||||
|
||||
if(client_connection_problems())
|
||||
{
|
||||
gfx_mapscreen(0, 0, 300*gfx_screenaspect(), 300);
|
||||
const char *text = "Connection Problems...";
|
||||
float w = gfx_text_width(0, 24, text, -1);
|
||||
gfx_text(0, 150*gfx_screenaspect()-w/2, 50, 24, text, -1);
|
||||
}
|
||||
|
||||
if(config.debug && local_character && local_prev_character)
|
||||
{
|
||||
gfx_mapscreen(0, 0, 300*gfx_screenaspect(), 300);
|
||||
|
@ -1496,5 +1489,73 @@ void render_game()
|
|||
render_goals(width/2-w/2, 150+750+25, w);
|
||||
render_spectators(width/2-w/2, 150+750+25+50+25, w);
|
||||
}
|
||||
|
||||
|
||||
|
||||
{
|
||||
gfx_mapscreen(0, 0, 300*gfx_screenaspect(), 300);
|
||||
|
||||
if(client_connection_problems())
|
||||
{
|
||||
const char *text = "Connection Problems...";
|
||||
float w = gfx_text_width(0, 24, text, -1);
|
||||
gfx_text(0, 150*gfx_screenaspect()-w/2, 50, 24, text, -1);
|
||||
}
|
||||
|
||||
tuning_params standard_tuning;
|
||||
|
||||
// render warning about non standard tuning
|
||||
bool flash = time_get()/(time_freq()/2)%2 == 0;
|
||||
if(config.cl_warning_tuning && memcmp(&standard_tuning, &tuning, sizeof(tuning_params)) != 0)
|
||||
{
|
||||
const char *text = "Warning! Server is running non-standard tuning.";
|
||||
if(flash)
|
||||
gfx_text_color(1,0.4f,0.4f,1.0f);
|
||||
else
|
||||
gfx_text_color(0.75f,0.2f,0.2f,1.0f);
|
||||
gfx_text(0x0, 5, 40, 6, text, -1);
|
||||
gfx_text_color(1,1,1,1);
|
||||
}
|
||||
|
||||
// render tuning debugging
|
||||
if(config.dbg_tuning)
|
||||
{
|
||||
float y = 50.0f;
|
||||
int count = 0;
|
||||
for(int i = 0; i < tuning.num(); i++)
|
||||
{
|
||||
char buf[128];
|
||||
float current, standard;
|
||||
tuning.get(i, ¤t);
|
||||
standard_tuning.get(i, &standard);
|
||||
|
||||
if(standard == current)
|
||||
gfx_text_color(1,1,1,1.0f);
|
||||
else
|
||||
gfx_text_color(1,0.25f,0.25f,1.0f);
|
||||
|
||||
float w;
|
||||
float x = 5.0f;
|
||||
|
||||
sprintf(buf, "%.2f", standard);
|
||||
x += 20.0f;
|
||||
w = gfx_text_width(0, 5, buf, -1);
|
||||
gfx_text(0x0, x-w, y+count*6, 5, buf, -1);
|
||||
|
||||
sprintf(buf, "%.2f", current);
|
||||
x += 20.0f;
|
||||
w = gfx_text_width(0, 5, buf, -1);
|
||||
gfx_text(0x0, x-w, y+count*6, 5, buf, -1);
|
||||
|
||||
x += 5.0f;
|
||||
gfx_text(0x0, x, y+count*6, 5, tuning.names[i], -1);
|
||||
|
||||
count++;
|
||||
}
|
||||
}
|
||||
|
||||
gfx_text_color(1,1,1,1);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
|
|
@ -25,6 +25,7 @@ extern const obj_player_character *local_prev_character;
|
|||
extern const obj_player_info *local_info;
|
||||
extern const obj_flag *flags[2];
|
||||
extern const obj_game *gameobj;
|
||||
extern tuning_params tuning;
|
||||
|
||||
// predicted players
|
||||
extern player_core predicted_prev_player;
|
||||
|
|
|
@ -39,6 +39,8 @@ static float time_now()
|
|||
return float(time_get()-time_start)/float(time_freq());
|
||||
}
|
||||
|
||||
|
||||
|
||||
static void client_console_print(const char *str)
|
||||
{
|
||||
int len = strlen(str);
|
||||
|
@ -66,39 +68,21 @@ static void client_console_print(const char *str)
|
|||
//dbg_msg("console", "FROM CLIENT!! %s", str);
|
||||
}
|
||||
|
||||
static void connect_command(struct lexer_result *result, void *user_data)
|
||||
{
|
||||
const char *address;
|
||||
extract_result_string(result, 1, &address);
|
||||
client_connect(address);
|
||||
}
|
||||
|
||||
static void disconnect_command(struct lexer_result *result, void *user_data)
|
||||
{
|
||||
client_disconnect();
|
||||
}
|
||||
|
||||
static void quit_command(struct lexer_result *result, void *user_data)
|
||||
{
|
||||
client_quit();
|
||||
}
|
||||
|
||||
static void con_team(struct lexer_result *result, void *user_data)
|
||||
static void con_team(void *result, void *user_data)
|
||||
{
|
||||
int new_team;
|
||||
extract_result_int(result, 1, &new_team);
|
||||
console_result_int(result, 1, &new_team);
|
||||
send_switch_team(new_team);
|
||||
}
|
||||
|
||||
void client_console_init()
|
||||
{
|
||||
console_register_print_callback(client_console_print);
|
||||
MACRO_REGISTER_COMMAND("quit", "", quit_command, 0x0);
|
||||
MACRO_REGISTER_COMMAND("connect", "s", connect_command, 0x0);
|
||||
MACRO_REGISTER_COMMAND("disconnect", "", disconnect_command, 0x0);
|
||||
MACRO_REGISTER_COMMAND("team", "i", con_team, 0x0);
|
||||
}
|
||||
|
||||
|
||||
void console_handle_input()
|
||||
{
|
||||
int was_active = console_active();
|
||||
|
|
|
@ -5,6 +5,7 @@
|
|||
extern "C" {
|
||||
#include <engine/e_config.h>
|
||||
#include <engine/client/ec_font.h>
|
||||
#include <engine/e_console.h>
|
||||
};
|
||||
|
||||
#include <game/generated/gc_data.h>
|
||||
|
@ -25,7 +26,7 @@ extern void menu_init();
|
|||
extern bool menu_active;
|
||||
extern bool menu_game_active;
|
||||
|
||||
extern "C" void modc_preinit()
|
||||
extern "C" void modc_console_init()
|
||||
{
|
||||
client_console_init();
|
||||
}
|
||||
|
@ -109,6 +110,7 @@ extern "C" void modc_predict()
|
|||
|
||||
// repredict player
|
||||
world_core world;
|
||||
world.tuning = tuning;
|
||||
int local_cid = -1;
|
||||
|
||||
// search for players
|
||||
|
@ -437,10 +439,15 @@ extern "C" void modc_message(int msg)
|
|||
|
||||
client_datas[cid].update_render_info();
|
||||
}
|
||||
else if(msg == MSG_TUNE_PARAMS)
|
||||
{
|
||||
int *params = (int *)&tuning;
|
||||
for(unsigned i = 0; i < sizeof(tuning_params)/sizeof(int); i++)
|
||||
params[i] = msg_unpack_int();
|
||||
}
|
||||
else if(msg == MSG_WEAPON_PICKUP)
|
||||
{
|
||||
int weapon = msg_unpack_int();
|
||||
|
||||
picked_up_weapon = weapon+1;
|
||||
}
|
||||
else if(msg == MSG_READY_TO_ENTER)
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
#include <math.h>
|
||||
#include "array.h"
|
||||
#include "../g_mapitems.h"
|
||||
#include "../g_math.h"
|
||||
#include "../client/gc_render.h"
|
||||
|
||||
extern "C" {
|
||||
|
|
|
@ -1,6 +1,50 @@
|
|||
/* copyright (c) 2007 magnus auvinen, see licence.txt for more info */
|
||||
#include <string.h>
|
||||
#include "g_game.h"
|
||||
|
||||
const char *tuning_params::names[] =
|
||||
{
|
||||
#define MACRO_TUNING_PARAM(name,value) #name,
|
||||
#include "g_tuning.h"
|
||||
#undef MACRO_TUNING_PARAM
|
||||
};
|
||||
|
||||
|
||||
bool tuning_params::set(int index, float value)
|
||||
{
|
||||
if(index < 0 || index >= num())
|
||||
return false;
|
||||
((tune_param *)this)[index] = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool tuning_params::get(int index, float *value)
|
||||
{
|
||||
if(index < 0 || index >= num())
|
||||
return false;
|
||||
*value = (float)((tune_param *)this)[index];
|
||||
return true;
|
||||
}
|
||||
|
||||
bool tuning_params::set(const char *name, float value)
|
||||
{
|
||||
for(int i = 0; i < num(); i++)
|
||||
if(strcmp(name, names[i]) == 0)
|
||||
return set(i, value);
|
||||
return false;
|
||||
}
|
||||
|
||||
bool tuning_params::get(const char *name, float *value)
|
||||
{
|
||||
for(int i = 0; i < num(); i++)
|
||||
if(strcmp(name, names[i]) == 0)
|
||||
return get(i, value);
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
// TODO: OPT: rewrite this smarter!
|
||||
void move_point(vec2 *inout_pos, vec2 *inout_vel, float elasticity, int *bounces)
|
||||
{
|
||||
|
@ -125,11 +169,11 @@ void player_core::tick()
|
|||
|
||||
vec2 direction = normalize(vec2(input.target_x, input.target_y));
|
||||
|
||||
vel.y += gravity;
|
||||
vel.y += world->tuning.gravity;
|
||||
|
||||
float max_speed = grounded ? ground_control_speed : air_control_speed;
|
||||
float accel = grounded ? ground_control_accel : air_control_accel;
|
||||
float friction = grounded ? ground_friction : air_friction;
|
||||
float max_speed = grounded ? world->tuning.ground_control_speed : world->tuning.air_control_speed;
|
||||
float accel = grounded ? world->tuning.ground_control_accel : world->tuning.air_control_accel;
|
||||
float friction = grounded ? world->tuning.ground_friction : world->tuning.air_friction;
|
||||
|
||||
// handle movement
|
||||
if(input.left)
|
||||
|
@ -153,13 +197,13 @@ void player_core::tick()
|
|||
if(grounded)
|
||||
{
|
||||
triggered_events |= COREEVENT_GROUND_JUMP;
|
||||
vel.y = -ground_jump_speed;
|
||||
vel.y = -world->tuning.ground_jump_impulse;
|
||||
jumped |= 1;
|
||||
}
|
||||
else if(!(jumped&2))
|
||||
{
|
||||
triggered_events |= COREEVENT_AIR_JUMP;
|
||||
vel.y = -ground_air_speed;
|
||||
vel.y = -world->tuning.air_jump_impulse;
|
||||
jumped |= 3;
|
||||
}
|
||||
}
|
||||
|
@ -181,7 +225,7 @@ void player_core::tick()
|
|||
}
|
||||
else if(hook_state == HOOK_FLYING)
|
||||
{
|
||||
vec2 new_pos = hook_pos+hook_dir*hook_fire_speed;
|
||||
vec2 new_pos = hook_pos+hook_dir*world->tuning.hook_fire_speed;
|
||||
|
||||
// Check against other players first
|
||||
for(int i = 0; i < MAX_CLIENTS; i++)
|
||||
|
@ -223,7 +267,7 @@ void player_core::tick()
|
|||
hook_state = HOOK_GRABBED;
|
||||
hook_pos = new_pos;
|
||||
}
|
||||
else if(distance(pos, new_pos) > hook_length)
|
||||
else if(distance(pos, new_pos) > world->tuning.hook_length)
|
||||
{
|
||||
triggered_events |= COREEVENT_HOOK_RETRACT;
|
||||
hook_state = HOOK_RETRACTED;
|
||||
|
@ -270,7 +314,7 @@ void player_core::tick()
|
|||
// don't do this hook rutine when we are hook to a player
|
||||
if(hooked_player == -1 && distance(hook_pos, pos) > 46.0f)
|
||||
{
|
||||
vec2 hookvel = normalize(hook_pos-pos)*hook_drag_accel;
|
||||
vec2 hookvel = normalize(hook_pos-pos)*world->tuning.hook_drag_accel;
|
||||
// the hook as more power to drag you up then down.
|
||||
// this makes it easier to get on top of an platform
|
||||
if(hookvel.y > 0)
|
||||
|
@ -286,7 +330,7 @@ void player_core::tick()
|
|||
vec2 new_vel = vel+hookvel;
|
||||
|
||||
// check if we are under the legal limit for the hook
|
||||
if(length(new_vel) < hook_drag_speed || length(new_vel) < length(vel))
|
||||
if(length(new_vel) < world->tuning.hook_drag_speed || length(new_vel) < length(vel))
|
||||
vel = new_vel; // no problem. apply
|
||||
|
||||
}
|
||||
|
@ -333,23 +377,24 @@ void player_core::tick()
|
|||
{
|
||||
if(d > phys_size*1.50f) // TODO: fix tweakable variable
|
||||
{
|
||||
float accel = hook_drag_accel * (d/hook_length);
|
||||
float accel = world->tuning.hook_drag_accel * (d/world->tuning.hook_length);
|
||||
float drag_speed = world->tuning.hook_drag_speed;
|
||||
|
||||
// add force to the hooked player
|
||||
p->vel.x = saturated_add(-hook_drag_speed, hook_drag_speed, p->vel.x, accel*dir.x*1.5f);
|
||||
p->vel.y = saturated_add(-hook_drag_speed, hook_drag_speed, p->vel.y, accel*dir.y*1.5f);
|
||||
p->vel.x = saturated_add(-drag_speed, drag_speed, p->vel.x, accel*dir.x*1.5f);
|
||||
p->vel.y = saturated_add(-drag_speed, drag_speed, p->vel.y, accel*dir.y*1.5f);
|
||||
|
||||
// add a little bit force to the guy who has the grip
|
||||
vel.x = saturated_add(-hook_drag_speed, hook_drag_speed, vel.x, -accel*dir.x*0.25f);
|
||||
vel.y = saturated_add(-hook_drag_speed, hook_drag_speed, vel.y, -accel*dir.y*0.25f);
|
||||
vel.x = saturated_add(-drag_speed, drag_speed, vel.x, -accel*dir.x*0.25f);
|
||||
vel.y = saturated_add(-drag_speed, drag_speed, vel.y, -accel*dir.y*0.25f);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// clamp the velocity to something sane
|
||||
if(length(vel) > terminal_velocity)
|
||||
vel = normalize(vel) * terminal_velocity;
|
||||
if(length(vel) > world->tuning.terminal_velocity)
|
||||
vel = normalize(vel) * world->tuning.terminal_velocity;
|
||||
}
|
||||
|
||||
void player_core::move()
|
||||
|
|
|
@ -4,12 +4,35 @@
|
|||
|
||||
#include <engine/e_system.h>
|
||||
#include <engine/e_common_interface.h>
|
||||
#include <game/g_math.h>
|
||||
#include <math.h>
|
||||
#include "g_math.h"
|
||||
#include "g_collision.h"
|
||||
|
||||
#include "g_protocol.h"
|
||||
|
||||
struct tuning_params
|
||||
{
|
||||
tuning_params()
|
||||
{
|
||||
const float ticks_per_second = 50.0f;
|
||||
#define MACRO_TUNING_PARAM(name,value) name = value;
|
||||
#include "g_tuning.h"
|
||||
#undef MACRO_TUNING_PARAM
|
||||
}
|
||||
|
||||
static const char *names[];
|
||||
|
||||
#define MACRO_TUNING_PARAM(name,value) tune_param name;
|
||||
#include "g_tuning.h"
|
||||
#undef MACRO_TUNING_PARAM
|
||||
|
||||
static int num() { return sizeof(tuning_params)/sizeof(int); }
|
||||
bool set(int index, float value);
|
||||
bool set(const char *name, float value);
|
||||
bool get(int index, float *value);
|
||||
bool get(const char *name, float *value);
|
||||
};
|
||||
|
||||
|
||||
inline vec2 get_direction(int angle)
|
||||
{
|
||||
float a = angle/256.0f;
|
||||
|
@ -90,7 +113,8 @@ public:
|
|||
{
|
||||
mem_zero(players, sizeof(players));
|
||||
}
|
||||
|
||||
|
||||
tuning_params tuning;
|
||||
class player_core *players[MAX_CLIENTS];
|
||||
};
|
||||
|
||||
|
|
|
@ -158,9 +158,4 @@ typedef struct
|
|||
int name;
|
||||
} MAPITEM_ENVELOPE;
|
||||
|
||||
// float to fixed
|
||||
inline int f2fx(float v) { return (int)(v*(float)(1<<10)); }
|
||||
inline float fx2f(int v) { return v*(1.0f/(1<<10)); }
|
||||
|
||||
|
||||
#endif
|
||||
|
|
|
@ -27,6 +27,32 @@ inline T mix(const T a, const T b, TB amount)
|
|||
|
||||
inline float frandom() { return rand()/(float)(RAND_MAX); }
|
||||
|
||||
// float to fixed
|
||||
inline int f2fx(float v) { return (int)(v*(float)(1<<10)); }
|
||||
inline float fx2f(int v) { return v*(1.0f/(1<<10)); }
|
||||
|
||||
class fxp
|
||||
{
|
||||
int value;
|
||||
public:
|
||||
void set(int v) { value = v; }
|
||||
int get() const { return value; }
|
||||
fxp &operator = (int v) { value = v<<10; return *this; }
|
||||
fxp &operator = (float v) { value = (int)(v*(float)(1<<10)); return *this; }
|
||||
operator float() const { return value/(float)(1<<10); }
|
||||
};
|
||||
|
||||
class tune_param
|
||||
{
|
||||
int value;
|
||||
public:
|
||||
void set(int v) { value = v; }
|
||||
int get() const { return value; }
|
||||
tune_param &operator = (int v) { value = (int)(v*100.0f); return *this; }
|
||||
tune_param &operator = (float v) { value = (int)(v*100.0f); return *this; }
|
||||
operator float() const { return value/100.0f; }
|
||||
};
|
||||
|
||||
const float pi = 3.1415926535897932384626433f;
|
||||
|
||||
template <typename T> inline T min(T a, T b) { return a<b?a:b; }
|
||||
|
|
|
@ -4,27 +4,6 @@
|
|||
#ifndef GAME_PROTOCOL_H
|
||||
#define GAME_PROTOCOL_H
|
||||
|
||||
// --------- PHYSICS TWEAK! --------
|
||||
const float ticks_per_second = 50.0f;
|
||||
const float ground_control_speed = 350.0f / ticks_per_second;
|
||||
const float ground_control_accel = 100.0f / ticks_per_second;
|
||||
const float ground_friction = 0.5f;
|
||||
const float ground_jump_speed = 12.6f;
|
||||
const float ground_air_speed = 11.5f;
|
||||
const float air_control_speed = 250.0f / ticks_per_second;
|
||||
const float air_control_accel = 1.5f;
|
||||
const float air_friction = 0.95f;
|
||||
const float hook_length = 34*10.0f;
|
||||
const float hook_fire_speed = 45.0f;
|
||||
const float hook_drag_accel = 3.0f;
|
||||
const float hook_drag_speed = 15.0f;
|
||||
const float gravity = 0.5f;
|
||||
const float terminal_velocity = 20.0f;
|
||||
|
||||
const float wall_friction = 0.80f;
|
||||
const float wall_jump_speed_up = ground_jump_speed*0.8f;
|
||||
const float wall_jump_speed_out = ground_jump_speed*0.8f;
|
||||
|
||||
// Network stuff
|
||||
enum
|
||||
{
|
||||
|
@ -62,6 +41,7 @@ enum
|
|||
MSG_READY_TO_ENTER, // server -> client
|
||||
MSG_WEAPON_PICKUP,
|
||||
MSG_SOUND_GLOBAL,
|
||||
MSG_TUNE_PARAMS,
|
||||
};
|
||||
|
||||
enum
|
||||
|
|
17
src/game/g_tuning.h
Normal file
17
src/game/g_tuning.h
Normal file
|
@ -0,0 +1,17 @@
|
|||
/* physics tuning */
|
||||
MACRO_TUNING_PARAM(ground_control_speed, 350.0f / ticks_per_second)
|
||||
MACRO_TUNING_PARAM(ground_control_accel, 100.0f / ticks_per_second)
|
||||
MACRO_TUNING_PARAM(ground_friction, 0.5f)
|
||||
MACRO_TUNING_PARAM(ground_jump_impulse, 12.6f)
|
||||
MACRO_TUNING_PARAM(air_jump_impulse, 11.5f)
|
||||
MACRO_TUNING_PARAM(air_control_speed, 250.0f / ticks_per_second)
|
||||
MACRO_TUNING_PARAM(air_control_accel, 1.5f)
|
||||
MACRO_TUNING_PARAM(air_friction, 0.95f)
|
||||
MACRO_TUNING_PARAM(hook_length, 34*10.0f)
|
||||
MACRO_TUNING_PARAM(hook_fire_speed, 45.0f)
|
||||
MACRO_TUNING_PARAM(hook_drag_accel, 3.0f)
|
||||
MACRO_TUNING_PARAM(hook_drag_speed, 15.0f)
|
||||
MACRO_TUNING_PARAM(gravity, 0.5f)
|
||||
MACRO_TUNING_PARAM(terminal_velocity, 1000.0f / ticks_per_second)
|
||||
|
||||
/* weapon tuning */
|
|
@ -34,6 +34,9 @@ MACRO_CONFIG_INT(cl_autoswitch_weapons, 0, 0, 1)
|
|||
MACRO_CONFIG_INT(cl_show_player_ids, 0, 0, 1)
|
||||
|
||||
|
||||
MACRO_CONFIG_INT(cl_warning_tuning, 1, 0, 1)
|
||||
|
||||
|
||||
MACRO_CONFIG_INT(cl_flow, 0, 0, 1)
|
||||
|
||||
MACRO_CONFIG_INT(cl_show_welcome, 1, 0, 1)
|
||||
|
@ -46,6 +49,7 @@ MACRO_CONFIG_STR(player_skin, 64, "default")
|
|||
MACRO_CONFIG_INT(dbg_bots, 0, 0, 11)
|
||||
MACRO_CONFIG_INT(dbg_firedelay, 0, 0, 1)
|
||||
MACRO_CONFIG_INT(dbg_flow, 0, 0, 1)
|
||||
MACRO_CONFIG_INT(dbg_tuning, 0, 0, 1)
|
||||
|
||||
MACRO_CONFIG_INT(ui_page, 1, 0, 5)
|
||||
MACRO_CONFIG_STR(ui_server_address, 128, "localhost:8303")
|
||||
|
|
|
@ -3,6 +3,8 @@
|
|||
#include "../generated/gs_data.h"
|
||||
|
||||
|
||||
extern tuning_params tuning;
|
||||
|
||||
void create_sound_global(int sound, int target=-1);
|
||||
|
||||
inline int cmask_all() { return -1; }
|
||||
|
|
|
@ -151,7 +151,7 @@ void gameobject_ctf::tick()
|
|||
}
|
||||
else
|
||||
{
|
||||
f->vel.y += gravity;
|
||||
f->vel.y += world->core.tuning.gravity;
|
||||
move_box(&f->pos, &f->vel, vec2(f->phys_size, f->phys_size), 0.5f);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -14,6 +14,8 @@
|
|||
|
||||
data_container *data = 0x0;
|
||||
|
||||
tuning_params tuning;
|
||||
|
||||
class player* get_player(int index);
|
||||
void create_damageind(vec2 p, float angle_mod, int amount);
|
||||
void create_explosion(vec2 p, int owner, int weapon, bool bnodamage);
|
||||
|
@ -58,6 +60,16 @@ void send_chat(int cid, int team, const char *msg)
|
|||
}
|
||||
|
||||
|
||||
void send_tuning_params(int cid)
|
||||
{
|
||||
msg_pack_start(MSG_TUNE_PARAMS, MSGFLAG_VITAL);
|
||||
int *params = (int *)&tuning;
|
||||
for(unsigned i = 0; i < sizeof(tuning_params)/sizeof(int); i++)
|
||||
msg_pack_int(params[i]);
|
||||
msg_pack_end();
|
||||
server_send_msg(cid);
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////
|
||||
// Event handler
|
||||
//////////////////////////////////////////////////
|
||||
|
@ -1670,7 +1682,7 @@ player* intersect_player(vec2 pos0, vec2 pos1, vec2& new_pos, entity* notthis)
|
|||
// Server hooks
|
||||
void mods_tick()
|
||||
{
|
||||
// clear all events
|
||||
world->core.tuning = tuning;
|
||||
world->tick();
|
||||
|
||||
if(world->paused) // make sure that the game object always updates
|
||||
|
@ -1858,13 +1870,19 @@ void mods_message(int msg, int client_id)
|
|||
|
||||
if(msg == MSG_STARTINFO)
|
||||
{
|
||||
// a client that connected!
|
||||
|
||||
// send all info to this client
|
||||
for(int i = 0; i < MAX_CLIENTS; i++)
|
||||
{
|
||||
if(players[i].client_id != -1)
|
||||
send_info(i, client_id);
|
||||
}
|
||||
|
||||
// send tuning parameters to client
|
||||
send_tuning_params(client_id);
|
||||
|
||||
//
|
||||
msg_pack_start(MSG_READY_TO_ENTER, MSGFLAG_VITAL);
|
||||
msg_pack_end();
|
||||
server_send_msg(client_id);
|
||||
|
@ -1881,6 +1899,57 @@ void mods_message(int msg, int client_id)
|
|||
|
||||
extern unsigned char internal_data[];
|
||||
|
||||
|
||||
static void con_tune_param(void *result, void *user_data)
|
||||
{
|
||||
const char *param_name;
|
||||
float new_value;
|
||||
|
||||
if(console_result_string(result, 1, ¶m_name) == 0)
|
||||
{
|
||||
if(console_result_float(result, 2, &new_value) == 0)
|
||||
{
|
||||
if(tuning.set(param_name, new_value))
|
||||
{
|
||||
dbg_msg("tuning", "%s changed to %.2f", param_name, new_value);
|
||||
send_tuning_params(-1);
|
||||
}
|
||||
else
|
||||
console_print("No such tuning parameter");
|
||||
}
|
||||
else
|
||||
{
|
||||
//console_print("");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void con_tune_reset(void *result, void *user_data)
|
||||
{
|
||||
tuning_params p;
|
||||
tuning = p;
|
||||
send_tuning_params(-1);
|
||||
console_print("tuning reset");
|
||||
}
|
||||
|
||||
static void con_tune_dump(void *result, void *user_data)
|
||||
{
|
||||
for(int i = 0; i < tuning.num(); i++)
|
||||
{
|
||||
float v;
|
||||
tuning.get(i, &v);
|
||||
dbg_msg("tuning", "%s %.2f", tuning.names[i], v);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void mods_console_init()
|
||||
{
|
||||
MACRO_REGISTER_COMMAND("tune", "s?i", con_tune_param, 0);
|
||||
MACRO_REGISTER_COMMAND("tune_reset", "", con_tune_reset, 0);
|
||||
MACRO_REGISTER_COMMAND("tune_dump", "", con_tune_dump, 0);
|
||||
}
|
||||
|
||||
void mods_init()
|
||||
{
|
||||
if(!data) /* only load once */
|
||||
|
|
Loading…
Reference in a new issue