AMX Mod X Plugin Approver
|
07-07-2013
, 14:36
Re: Code doesn't work
|
#12
|
entity_get_float like pev have to handle all concerned constants. So you have more code.
Well easy to check :
get_user_maxspeed()
Code:
static cell AMX_NATIVE_CALL get_user_maxspeed(AMX *amx, cell *params) // Float:get_user_maxspeed(index) = 1 argument
{
// Gets user maxspeed.
// params[1] = index
// Check index
CHECK_PLAYER(params[1]);
// Fetch player pointer
edict_t *pPlayer = MF_GetPlayerEdict(params[1]);
return amx_ftoc(pPlayer->v.maxspeed);
}
entity_get_float()
Code:
static cell AMX_NATIVE_CALL entity_get_float(AMX *amx, cell *params)
{
int iEnt = params[1];
int idx = params[2];
REAL fVal = 0;
CHECK_ENTITY_SIMPLE(iEnt);
edict_t *pEnt = INDEXENT2(iEnt);
switch (idx)
{
case impacttime:
fVal = pEnt->v.impacttime;
break;
case starttime:
fVal = pEnt->v.starttime;
break;
case idealpitch:
fVal = pEnt->v.idealpitch;
break;
case pitch_speed:
fVal = pEnt->v.pitch_speed;
break;
case ideal_yaw:
fVal = pEnt->v.ideal_yaw;
break;
case yaw_speed:
fVal = pEnt->v.yaw_speed;
break;
case ltime:
fVal = pEnt->v.ltime;
break;
case nextthink:
fVal = pEnt->v.nextthink;
break;
case gravity:
fVal = pEnt->v.gravity;
break;
case friction:
fVal = pEnt->v.friction;
break;
case frame:
fVal = pEnt->v.frame;
break;
case animtime:
fVal = pEnt->v.animtime;
break;
case framerate:
fVal = pEnt->v.framerate;
break;
case health:
fVal = pEnt->v.health;
break;
case frags:
fVal = pEnt->v.frags;
break;
case takedamage:
fVal = pEnt->v.takedamage;
break;
case max_health:
fVal = pEnt->v.max_health;
break;
case teleport_time:
fVal = pEnt->v.teleport_time;
break;
case armortype:
fVal = pEnt->v.armortype;
break;
case armorvalue:
fVal = pEnt->v.armorvalue;
break;
case dmg_take:
fVal = pEnt->v.dmg_take;
break;
case dmg_save:
fVal = pEnt->v.dmg_save;
break;
case dmg:
fVal = pEnt->v.dmg;
break;
case dmgtime:
fVal = pEnt->v.dmgtime;
break;
case speed:
fVal = pEnt->v.speed;
break;
case air_finished:
fVal = pEnt->v.air_finished;
break;
case pain_finished:
fVal = pEnt->v.pain_finished;
break;
case radsuit_finished:
fVal = pEnt->v.radsuit_finished;
break;
case scale:
fVal = pEnt->v.scale;
break;
case renderamt:
fVal = pEnt->v.renderamt;
break;
case maxspeed:
fVal = pEnt->v.maxspeed;
break;
case fov:
fVal = pEnt->v.fov;
break;
case flFallVelocity:
fVal = pEnt->v.flFallVelocity;
break;
case fuser1:
fVal = pEnt->v.fuser1;
break;
case fuser2:
fVal = pEnt->v.fuser2;
break;
case fuser3:
fVal = pEnt->v.fuser3;
break;
case fuser4:
fVal = pEnt->v.fuser4;
break;
default:
return 0;
break;
}
return amx_ftoc(fVal);
}
pev()
Code:
static cell AMX_NATIVE_CALL amx_pev(AMX *amx,cell *params)
{
int index = params[1];
CHECK_ENTITY(index);
edict_t *pEdict = INDEXENT2(index);
int iSwitch = params[2];
//onto normal cases - sanity check
if (iSwitch <= pev_string_start || iSwitch >= pev_absolute_end)
{
MF_LogError(amx, AMX_ERR_NATIVE, "Undefined pev index: %d", iSwitch);
return 0;
}
int offs = g_offset_table[iSwitch];
//sanity check #2
if (offs == -1)
{
MF_LogError(amx, AMX_ERR_NATIVE, "Undefined pev index: %d", iSwitch);
return 0;
}
enum
{
Ret_Int = (1<<0),
Ret_Float = (1<<1),
Ret_Vec = (1<<2),
Ret_ByteArray = (1<<3),
Ret_String = (1<<4),
Ret_Edict = (1<<5),
Ret_Bytes2 = (1<<6),
Ret_Bytes4 = (1<<7)
};
union
{
int i;
float f;
byte b;
string_t s;
byte ba[4];
} rets;
Vector vr;
int ValType = 0;
entvars_t *v = &(pEdict->v);
//get primitive data types
if (iSwitch > pev_int_start && iSwitch < pev_int_end)
{
rets.i = *(int *)EDICT_OFFS(v, offs);
ValType = Ret_Int;
} else if (iSwitch > pev_float_start && iSwitch < pev_float_end) {
rets.f = *(float *)EDICT_OFFS(v, offs);
ValType = Ret_Float;
} else if (iSwitch > pev_vecarray_start && iSwitch < pev_vecarray_end) {
vr = *(vec3_t *)EDICT_OFFS(v, offs);
ValType = Ret_Vec;
} else if (iSwitch > pev_bytearray_start && iSwitch < pev_bytearray_end) {
if (iSwitch == controller)
{
rets.ba[0] = v->controller[0];
rets.ba[1] = v->controller[1];
rets.ba[2] = v->controller[2];
rets.ba[3] = v->controller[3];
ValType = Ret_Bytes4;
} else {
rets.ba[0] = v->blending[0];
rets.ba[1] = v->blending[1];
ValType = Ret_Bytes2;
}
} else if (iSwitch > pev_byte_start && iSwitch < pev_byte_end) {
rets.b = *(byte *)EDICT_OFFS(v, offs);
ValType = Ret_Int;
} else if ( (iSwitch > pev_string_start && iSwitch < pev_string_end)
|| (iSwitch > pev_string2_begin && iSwitch < pev_string2_end) ) {
rets.s = *(string_t *)EDICT_OFFS(v, offs);
ValType = Ret_String;
} else if ( (iSwitch > pev_edict_start && iSwitch < pev_edict_end)
|| (iSwitch > pev_edict2_start && iSwitch < pev_absolute_end) ) {
edict_t *e = *(edict_t **)EDICT_OFFS(v, offs);
rets.i = ENTINDEX(e);
ValType = Ret_Int;
ValType |= Ret_Edict;
}
size_t count = params[0] / sizeof(cell) - 2;
if (count == 0)
{
//return an int
if (ValType & Ret_Int)
{
return rets.i;
} else if (ValType == Ret_Float) {
return (cell)rets.f;
} else if (ValType == Ret_String) {
return (cell)rets.s;
} else {
MF_LogError(amx, AMX_ERR_NATIVE, "Invalid return type");
return 0;
}
} else if (count == 1) {
//return a byref float - usually
cell *addr = MF_GetAmxAddr(amx, params[3]);
if (ValType == Ret_Float)
{
*addr = amx_ftoc(rets.f);
} else if (ValType == Ret_Int) {
REAL f = (REAL)rets.i;
*addr = amx_ftoc(f);
} else if (ValType == Ret_Vec) {
addr[0] = amx_ftoc(vr.x);
addr[1] = amx_ftoc(vr.y);
addr[2] = amx_ftoc(vr.z);
} else if (ValType == Ret_Bytes2) {
addr[0] = rets.ba[0];
addr[1] = rets.ba[1];
} else if (ValType == Ret_Bytes4) {
addr[0] = rets.ba[0];
addr[1] = rets.ba[1];
addr[2] = rets.ba[2];
addr[3] = rets.ba[3];
} else {
MF_LogError(amx, AMX_ERR_NATIVE, "Invalid return type");
return 0;
}
return 1;
} else if (count == 2) {
cell size = *(MF_GetAmxAddr(amx, params[4]));
if (ValType == Ret_String)
{
const char *str = STRING(rets.s);
if (!str)
str = "";
int num = MF_SetAmxString(amx, params[3], str, size);
return num;
} else if (ValType & Ret_Int) {
char temp[32];
snprintf(temp, 31, "%d", rets.i);
return MF_SetAmxString(amx, params[3], temp, size);
} else if (ValType == Ret_Float) {
char temp[32];
snprintf(temp, 31, "%f", rets.f);
return MF_SetAmxString(amx, params[3], temp, size);
} else if (ValType == Ret_Vec) {
char temp[32];
snprintf(temp, 31, "%f %f %f", vr.x, vr.y, vr.z);
return MF_SetAmxString(amx, params[3], temp, size);
} else if (ValType == Ret_Bytes2) {
char temp[32];
snprintf(temp, 31, "%d %d", rets.ba[0], rets.ba[1]);
return MF_SetAmxString(amx, params[3], temp, size);
} else if (ValType == Ret_Bytes4) {
char temp[32];
snprintf(temp, 31, "%d %d %d %d", rets.ba[0], rets.ba[1], rets.ba[2], rets.ba[3]);
return MF_SetAmxString(amx, params[3], temp, size);
}
MF_LogError(amx, AMX_ERR_NATIVE, "Invalid return type");
} else if (count == 3) {
cell size = *(MF_GetAmxAddr(amx, params[5]));
if (ValType == Ret_String)
{
const char *str = STRING(rets.s);
cell *addr = MF_GetAmxAddr(amx, params[3]);
*addr = (cell)rets.s;
if (!str)
str = "";
int num = MF_SetAmxString(amx, params[4], str, size);
return num;
}
MF_LogError(amx, AMX_ERR_NATIVE, "Invalid return type");
}
//if we got here, something happened
MF_LogError(amx, AMX_ERR_NATIVE, "Unknown pev index or return combination %d", iSwitch);
return 0;
}
get_user_maxspeed() and entity_get_float() are almost the same. Just a switch as difference.
pev() has more code/check.
Theoretically, get_user_maxspeed() >= entity_get_float() > pev().
__________________
|
|