rpgxef/code/game/lua_mover.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

380 lines
9.6 KiB
C

// mover lib for lua
#include "g_lua.h"
#ifdef G_LUA
// mover.Halt(entity ent)
// Stops translational movement on ent immediately.
static int Mover_Halt(lua_State *L) {
lent_t *lent;
gentity_t *ent = NULL;
int id = 0;
if(lua_isnumber(L, 1)) {
id = luaL_checkint(L, 1);
if(id < 0 || id > MAX_GENTITIES - 1) return 1;
ent = &g_entities[id];
if(!ent) return 1;
} else {
lent = Lua_GetEntity(L, 1);
if(!lent || !lent->e) return 1;
ent = lent->e;
}
LUA_DEBUG("Mover_Halt - start: end=%d", ent->s.number);
BG_EvaluateTrajectory(&ent->s.pos, level.time, ent->r.currentOrigin);
VectorCopy(ent->r.currentOrigin, ent->s.pos.trBase);
ent->s.pos.trType = TR_STATIONARY;
ent->s.pos.trTime = level.time;
ent->nextthink = 0;
ent->think = NULL;
ent->nextTrain = NULL;
trap_LinkEntity(ent);
LUA_DEBUG("Mover_Halt - return: halted ent");
return 0;
}
// mover.HaltAngles(entity ent)
// Stops rotational movement on ent immediately.
static int Mover_HaltAngles(lua_State * L)
{
lent_t *lent;
gentity_t *ent = NULL;
int id = 0;
if(lua_isnumber(L, 1)) {
id = luaL_checkint(L, 1);
if(id < 0 || id > MAX_GENTITIES - 1) return 1;
ent = &g_entities[id];
if(!ent) return 1;
} else {
lent = Lua_GetEntity(L, 1);
if(!lent || !lent->e) return 1;
ent = lent->e;
}
LUA_DEBUG("Mover_HaltAngles - start: ent=%d", ent->s.number);
if(ent)
{
BG_EvaluateTrajectory(&ent->s.apos, level.time, ent->s.apos.trBase);
ent->s.apos.trType = TR_STATIONARY;
ent->s.apos.trTime = level.time;
trap_LinkEntity(ent);
LUA_DEBUG("Mover_HaltAngles - return: halted ent");
}
return 0;
}
extern void Reached_Train(gentity_t *ent);
extern void Think_SetupTrainTargets(gentity_t *ent);
extern void SetMoverState(gentity_t *ent, moverState_t moverState, int time);
// mover.AsTrain(entity mover, entity target, float speed)
// Moves an entity like a func_train entity. Targets have to be path_corner entities.
// * ent the entity to move
// * target the first path_corner to move to
// * speed speed to move to first path_corner with
static int Mover_AsTrain(lua_State * L)
{
lent_t *lent, *tlent;
gentity_t *ent = NULL;
gentity_t *targ = NULL;
vec3_t move;
float length;
int id = 0, tid = 0;
float speed = (float)luaL_checknumber(L, 3);
if(lua_isnumber(L, 1)) {
id = luaL_checkint(L, 1);
if(id < 0 || id > MAX_GENTITIES - 1) return 1;
ent = &g_entities[id];
if(!ent) return 1;
} else {
lent = Lua_GetEntity(L, 1);
if(!lent || !lent->e) return 1;
ent = lent->e;
}
if(luaL_checkint(L, 2)) {
tid = luaL_checkint(L, 2);
if(tid < 0 || tid > MAX_GENTITIES - 1) return 1;
targ = &g_entities[tid];
if(!targ) return 1;
} else {
tlent = Lua_GetEntity(L, 2);
if(!tlent || tlent->e) return 1;
targ = tlent->e;
}
LUA_DEBUG("Mover_AsTrain - start: ent=%d target=%d speed=%f", ent->s.number, targ->s.number, speed);
if(!ent || !targ)
{
LUA_DEBUG("Mover_AsTrain - return: ent or/and target missing");
return 0;
}
if(speed < 1)
{
LUA_DEBUG("Mover_AsTrain - moving: speed less than 1 fixed");
speed = 1;
}
if(ent->nextTrain)
{
LUA_DEBUG("Mover_AsTrain - pathing: NextTrain=%d ", ent->nextTrain->s.number);
}
ent->speed = speed;
ent->nextTrain = targ;
ent->reached = Reached_Train;
ent->target = G_NewString(targ->targetname);
Think_SetupTrainTargets(ent);
BG_EvaluateTrajectory(&ent->s.pos, level.time, ent->r.currentOrigin);
VectorCopy(ent->r.currentOrigin, ent->s.origin);
VectorCopy(ent->s.origin, ent->pos1);
VectorCopy(ent->nextTrain->s.origin, ent->pos2);
VectorSubtract(ent->pos2, ent->pos1, move);
length = VectorLength(move);
if(length <= 0.05)
{
G_SetOrigin(ent, ent->pos2);
LUA_DEBUG("Mover_AsTrain - return: snapped to target, length too small length=%f", length);
return 0;
}
ent->s.pos.trDuration = length * 1000 / speed;
ent->s.loopSound = ent->nextTrain->soundLoop;
SetMoverState(ent, MOVER_1TO2, level.time);
LUA_DEBUG("Mover_AsTrain - return: moving to target, length=%f duration=%d", length, ent->s.pos.trDuration);
return 0;
}
// mover.SetAngles(entity ent, vector angles) or
// mover.SetAngles(entity ent, float y, float z, float x)
// Sets the angles of ent to the specified value(s).
// Values are sorted Pitch (around Y-Axis), Yaw (around Z-Axis) and
// Roll (around X-Axis). These can also be stowed in a vector angles.
static int Mover_SetAngles(lua_State * L)
{
vec3_t newAngles;
lent_t *lent;
gentity_t *ent = NULL;
vec_t *target;
int id = 0;
if(lua_isnumber(L, 1)) {
id = luaL_checkint(L, 1);
if(id < 0 || id > MAX_GENTITIES - 1) return 1;
ent = &g_entities[id];
if(!ent) return 1;
} else {
lent = Lua_GetEntity(L, 1);
if(!lent || !lent->e) return 1;
ent = lent->e;
}
if(Lua_IsVector(L, 2))
{
target = Lua_GetVector(L, 2);
VectorCopy(target, newAngles);
}
else
{
newAngles[0] = luaL_checkint(L, 2);
newAngles[1] = luaL_checkint(L, 3);
newAngles[2] = luaL_checkint(L, 4);
}
LUA_DEBUG("Mover_SetAngles - start: ent=%d angles=%s", ent->s.number, vtos(newAngles));
if(ent)
{
VectorCopy(newAngles, ent->s.apos.trBase);
VectorCopy(newAngles, ent->s.angles);
trap_LinkEntity(ent);
LUA_DEBUG("Mover_SetAngles - return: moved");
}
return 0;
}
// mover.SetPosition(entity ent, vector pos) or
// mover.SetPosition(entity ent, float x, float y, float z)
// Set the position of ent to the specified value(s). Can also be stowed in a vector pos.
static int Mover_SetPosition(lua_State * L)
{
vec3_t newOrigin;
lent_t *lent;
gentity_t *ent = NULL;
vec_t *target;
int id = 0;
if(lua_isnumber(L, 1)) {
id = luaL_checkint(L, 1);
if(id < 0 || id > MAX_GENTITIES - 1) return 1;
ent = &g_entities[id];
if(!ent) return 1;
} else {
lent = Lua_GetEntity(L, 1);
if(!lent || !lent->e) return 1;
ent = lent->e;
}
if(Lua_IsVector(L, 2))
{
target = Lua_GetVector(L, 2);
VectorCopy(target, newOrigin);
}
else
{
newOrigin[0] = luaL_checkint(L, 2);
newOrigin[1] = luaL_checkint(L, 3);
newOrigin[2] = luaL_checkint(L, 4);
}
LUA_DEBUG("Mover_SetPosition - start: ent=%d pos=%s", ent->s.number, vtos(newOrigin));
if(ent)
{
G_SetOrigin(ent, newOrigin);
trap_LinkEntity(ent);
LUA_DEBUG("Mover_SetPosition - return: moved");
}
return 0;
}
static void SetTrajectoryLinear(trajectory_t * tr, const float speed, const vec3_t endPosition)
{
vec3_t delta;
float length;
VectorSubtract(endPosition, tr->trBase, delta);
length = VectorLength(delta);
VectorNormalize(delta);
tr->trDuration = length * 1000 / speed;
tr->trTime = level.time;
VectorScale(delta, speed, tr->trDelta);
tr->trType = TR_LINEAR_STOP;
}
// mover.ToAngles(entity ent, float speed, vector angles) or
// mover.ToAngles(entity ent, float speed, float y, float z, float x)
// Rotates ent with speed speed (in degrees per second) to the specified value(s).
// Values are sorted Pitch (around Y-Axis), Yaw (around Z-Axis) and
// Roll (around X-Axis). These can also be stowed in a vector angles.
static int Mover_ToAngles(lua_State * L)
{
vec3_t newAngles;
lent_t *lent;
gentity_t *ent = NULL;
float speed;
vec_t *target;
int id = 0;
if(lua_isnumber(L, 1)) {
id = luaL_checkint(L, 1);
if(id < 0 || id > MAX_GENTITIES - 1) return 1;
ent = &g_entities[id];
if(!ent) return 1;
} else {
lent = Lua_GetEntity(L, 1);
if(!lent || !lent->e) return 1;
ent = lent->e;
}
speed = (float)luaL_checknumber(L, 2);
if(Lua_IsVector(L, 3))
{
target = Lua_GetVector(L, 3);
VectorCopy(target, newAngles);
}
else
{
newAngles[0] = luaL_checkint(L, 3);
newAngles[1] = luaL_checkint(L, 4);
newAngles[2] = luaL_checkint(L, 5);
}
LUA_DEBUG("Mover_ToAngles - start: ent=%d angles=%s speed=%f", ent->s.number, vtos(newAngles), speed);
if(ent)
{
BG_EvaluateTrajectory(&ent->s.apos, level.time, ent->s.apos.trBase);
SetTrajectoryLinear(&ent->s.apos, speed, newAngles);
ent->moverState = MOVER_LUA;
trap_LinkEntity(ent);
LUA_DEBUG("Mover_ToAngles - return: moving");
}
return 0;
}
// mover.ToPosition(entity ent, vector pos) or
// mover.ToPosition(entity ent, float x, float y, float z)
// Moves ent with speed speed to the specified value(s). Can also be stowed in a vector pos.
static int Mover_ToPosition(lua_State * L)
{
vec3_t newOrigin;
lent_t *lent;
gentity_t *ent = NULL;
float speed;
vec_t *target;
int id = 0;
if(lua_isnumber(L, 1)) {
id = luaL_checkint(L, 1);
if(id < 0 ||id > MAX_GENTITIES - 1) return 1;
ent = &g_entities[id];
if(!ent) return 1;
} else {
lent = Lua_GetEntity(L,1);
if(!lent || !lent->e) return 1;
ent = lent->e;
}
speed = (float)luaL_checknumber(L, 2);
if(Lua_IsVector(L, 3))
{
target = Lua_GetVector(L, 3);
VectorCopy(target, newOrigin);
}
else
{
newOrigin[0] = luaL_checkint(L, 3);
newOrigin[1] = luaL_checkint(L, 4);
newOrigin[2] = luaL_checkint(L, 5);
}
LUA_DEBUG("Mover_ToPosition - start: ent=%d pos=%s speed=%f", ent->s.number, vtos(newOrigin), speed);
if(ent)
{
BG_EvaluateTrajectory(&ent->s.pos, level.time, ent->s.pos.trBase);
SetTrajectoryLinear(&ent->s.pos, speed, newOrigin);
ent->moverState = MOVER_LUA;
trap_LinkEntity(ent);
LUA_DEBUG("Mover_ToPosition - return: moving");
}
return 0;
}
static const luaL_Reg lib_mover[] = {
{"Halt", Mover_Halt},
{"HaltAngles", Mover_HaltAngles},
{"AsTrain", Mover_AsTrain},
{"SetPosition", Mover_SetPosition},
{"SetOrigin", Mover_SetPosition},
{"ToPosition", Mover_ToPosition},
{"SetAngles", Mover_SetAngles},
{"ToAngles", Mover_ToAngles},
{NULL, NULL}
};
int Luaopen_Mover(lua_State *L) {
luaL_register(L, "mover", lib_mover);
return 1;
}
#endif