rpgxef/code/game/lua_game.c
Walter Julius Hennecke a39565b783 Integrated RPG-X2 rpgxEF edition into the rpgxEF repo
... not quite content with where the project files lie but it is ok for
now.
... compiling works fine so far (only tested mingw32 right now)
2012-08-04 12:54:37 +02:00

372 lines
8.5 KiB
C

// game lib for lua
#include "g_lua.h"
#ifdef G_LUA
// game.Print(string text)
// Prints text to the server console
static int Game_Print(lua_State *L) {
int i;
char buf[MAX_STRING_CHARS];
int n = lua_gettop(L);
memset(buf, 0, sizeof(buf));
lua_getglobal(L, "tostring");
LUA_DEBUG("Game_Print - start: ");
for(i = 1; i < n; i++)
{
const char *s;
lua_pushvalue(L, -1);
lua_pushvalue(L, i);
lua_call(L, 1, 1);
s = lua_tostring(L, -1);
if(s == NULL)
{
LUA_DEBUG("Game_Print - return: no string");
return luaL_error(L, "'tostring' must return a string to 'print'");
}
Q_strcat(buf, sizeof(buf), s);
lua_pop(L, 1);
}
G_Printf("%s\n", buf);
LUA_DEBUG("Game_Print - return: printed string");
return 0;
}
// game.CenterPrint(integer clientNum, string text)
// Prints text to the center of the screen of the client with client number clientNum.
// If clientNum is -1 the text gets printed for all clients.
static int Game_CenterPrint(lua_State *L) {
int i;
char buf[MAX_STRING_CHARS];
int n = lua_gettop(L);
int clNum = luaL_checknumber(L, 1);
memset(buf, 0, sizeof(buf));
lua_getglobal(L, "tostring");
LUA_DEBUG("Game_CenterPrint - start: ");
for(i = 1; i < n; i++)
{
const char *s;
lua_pushvalue(L, -1);
lua_pushvalue(L, i);
lua_call(L, 1, 1);
s = lua_tostring(L, 2);
if(s == NULL)
{
LUA_DEBUG("Game_CenterPrint - return: no string");
return luaL_error(L, "'tostring' must return a string to 'print'");
}
Q_strcat(buf, sizeof(buf), s);
lua_pop(L, 1);
}
trap_SendServerCommand(clNum, va("servercprint \"" S_COLOR_WHITE "%s\n\"", buf));
LUA_DEBUG("Game_CenterPrint - return: printed string");
return 0;
}
// game.ClientPrint(integer clientNum, string text)
// Prints text to the clients console that has the client number clientNum.
// If clientNum is -1 the text gets printed to all clients consoles.
static int Game_ClientPrint(lua_State *L) {
int i;
char buf[MAX_STRING_CHARS];
int n = lua_gettop(L);
int clNum = luaL_checknumber(L, 1);
gentity_t *player;
memset(buf, 0, sizeof(buf));
lua_getglobal(L, "tostring");
LUA_DEBUG("Game_ClientPrint - start: ");
for(i = 1; i < n; i++) {
const char *s;
lua_pushvalue(L, -1);
lua_pushvalue(L, i);
lua_call(L, 1, 1);
s = lua_tostring(L, 2);
if(s == NULL)
{
LUA_DEBUG("Game_ClientPrint - return: no string");
return luaL_error(L, "'tostring' must return a string to 'print'");
}
Q_strcat(buf, sizeof(buf), s);
lua_pop(L, 1);
}
if(clNum != -1) {
player = &g_entities[clNum];
if(player && player->client)
G_PrintfClient(player, "%s", buf);
} else
G_PrintfClientAll("%s", buf);
LUA_DEBUG("Game_ClientPrint - return: printed string");
return 0;
}
// game.MessagePrint(integer clientNum, string text)
// Prints text to the lower right corner of the screen of the client with client number clientNum.
// If clientNum is -1 the text gets printed for all clients.
static int Game_MessagePrint(lua_State *L) {
int i;
char buf[MAX_STRING_CHARS];
int n = lua_gettop(L);
int clNum = luaL_checknumber(L, 1);
memset(buf, 0, sizeof(buf));
lua_getglobal(L, "tostring");
LUA_DEBUG("Game_MessagePrint - start: ");
for(i = 1; i < n; i++)
{
const char *s;
lua_pushvalue(L, -1);
lua_pushvalue(L, i);
lua_call(L, 1, 1);
s = lua_tostring(L, 2);
if(s == NULL)
{
LUA_DEBUG("Game_MessagePrint - return: no string");
return luaL_error(L, "'tostring' must return a string to 'print'");
}
Q_strcat(buf, sizeof(buf), s);
lua_pop(L, 1);
}
trap_SendServerCommand(clNum, va("servermsg \"" S_COLOR_WHITE "%s\n\"", buf));
LUA_DEBUG("Game_MessagePrint - return: printed string");
return 0;
}
// game.SetGlobal(string name, value)
// Sets a global Lua variable which is called name to value.
// Creates a new global variable if a variable of name does not exist.
// value can be of any type.
static int Game_SetGlobal(lua_State *L) {
char *name;
name = (char *)luaL_checkstring(L, 1);
if(!name) return 0;
lua_pushvalue(L, 2);
lua_setglobal(L, name);
return 0;
}
// game.GetGlobal(string name)
// Returns the value of the global variable name.
// Returns nil if the variable does not exist.
static int Game_GetGlobal(lua_State *L) {
char *name;
name = (char *)luaL_checkstring(L, 1);
if(!name) return 0;
lua_getglobal(L, name);
return 1;
}
// Alert-Stuff... I don't know. I feel like removing this and stick to the entity spawning and setup.
// game.AlertSetup(entity ent, string greentarget, string yellowtarget, string redtarget, string bluetarget,
// string greensound, string yellowsound, string redsound, string bluesound, integer mode)
static int Game_AlertSetup(lua_State *L) {
if(luaAlertState) {
lua_pushboolean(L, 0);
return 1;
}
luaAlertState = (luaAlertState_t *)malloc(sizeof(luaAlertState_t));
if(!luaAlertState) {
lua_pushboolean(L, 0);
return 1;
}
luaAlertState->targets[0] = (char *)luaL_checkstring(L, 1);
luaAlertState->targets[1] = (char *)luaL_checkstring(L, 2);
luaAlertState->targets[2] = (char *)luaL_checkstring(L, 3);
luaAlertState->targets[3] = (char *)luaL_checkstring(L, 4);
luaAlertState->sounds[0] = (char *)luaL_checkstring(L, 5);
luaAlertState->sounds[1] = (char *)luaL_checkstring(L, 6);
luaAlertState->sounds[2] = (char *)luaL_checkstring(L, 7);
luaAlertState->sounds[3] = (char *)luaL_checkstring(L, 8);
luaAlertState->mode = luaL_checkint(L, 9);
luaAlertState->cond = 0;
lua_pushboolean(L, 1);
return 1;
}
static int Game_AlertAddShader(lua_State *L) {
int cond;
char *shader;
if(!luaAlertState) {
lua_pushboolean(L, 0);
return 1;
}
cond = luaL_checkint(L, 1);
if(cond < 0 || cond > 3) {
lua_pushboolean(L, 0);
return 1;
}
shader = (char *)luaL_checkstring(L, 2);
if(!shader || (strlen(shader) + 1) > MAX_QPATH) {
lua_pushboolean(L, 0);
return 1;
}
if(!luaAlertState->shaders[cond]) {
luaAlertState->shaders[cond] = (char *)malloc(sizeof(char) * (strlen(shader) + 1));
if(!luaAlertState->shaders[cond]) {
lua_pushboolean(L, 0);
return 1;
}
strncpy(luaAlertState->shaders[cond], shader, sizeof(luaAlertState->shaders[cond]));
} else {
void *tmp = realloc(luaAlertState->shaders[cond], sizeof(char) * (strlen(luaAlertState->shaders[cond]) +
strlen(shader) + 1));
if(!tmp){
lua_pushboolean(L, 0);
return 1;
}
luaAlertState->shaders[cond] = tmp;
Com_sprintf(luaAlertState->shaders[cond], sizeof(luaAlertState->shaders[cond]), "%s\0%s", luaAlertState->shaders[cond], shader);
}
lua_pushboolean(L, 1);
return 1;
}
// game.Alert(entity ent, integer target, boolean silent)
static int Game_Alert(lua_State *L) {
/*lent_t *lent;
int current, target;
qboolean silent;*/
return 0;
}
// game.LevelTime()
// Returns the current level time in milliseconds.
static int Game_Leveltime(lua_State * L)
{
lua_pushinteger(L, level.time);
LUA_DEBUG("Game_Leveltime - start/return: leveltime=%d", level.time);
return 1;
}
static int Game_Damage(lua_State *L) {
lent_t *lent;
gentity_t *targ = NULL, *inflictor = NULL, *attacker = NULL;
vec_t *dir = NULL, *point = NULL;
int damage = 0, dflags = 0, mod = 0;
lent = Lua_GetEntity(L, 1);
if(!lent || !lent->e) return 1;
targ = lent->e;
if(!lua_isnil(L, 2)) {
lent = Lua_GetEntity(L, 2);
if(lent && lent->e)
inflictor = lent->e;
}
if(!lua_isnil(L, 3)) {
lent = Lua_GetEntity(L, 3);
if(lent && lent->e)
attacker = lent->e;
}
if(!lua_isnil(L, 4))
dir = Lua_GetVector(L, 4);
if(!lua_isnil(L, 5))
point = Lua_GetVector(L, 5);
damage = (int)luaL_checknumber(L, 6);
dflags = (int)luaL_checknumber(L, 7);
mod = (int)luaL_checknumber(L, 8);
G_Damage(targ, inflictor, attacker, dir, point, damage, dflags, mod);
return 1;
}
static int Game_Repair(lua_State *L) {
lent_t *lent;
float rate;
lent = Lua_GetEntity(L, 1);
if(!lent || !lent->e) return 1;
rate = (float)luaL_checknumber(L, 2);
G_Repair(lent->e, NULL, rate); // FIXME ... trance ent?
return 1;
}
static const luaL_Reg lib_game[] = {
{"Damage", Game_Damage},
{"Repair", Game_Repair},
{"Print", Game_Print},
{"MessagePrint", Game_MessagePrint},
{"CenterPrint", Game_CenterPrint},
{"ClientPrint", Game_ClientPrint},
{"GetTime", Game_Leveltime},
{"AlertSetup", Game_AlertSetup},
{"AlertAddShader", Game_AlertAddShader},
{"Alert", Game_Alert},
{"SetGlobal", Game_SetGlobal},
{"GetGlobal", Game_GetGlobal},
{NULL, NULL}
};
int Luaopen_Game(lua_State *L) {
luaL_register(L, "game", lib_game);
lua_pushliteral(L, "_GAMEVERSION");
lua_pushliteral(L, GAMEVERSION);
return 1;
}
#endif