La verdad me la pase pensando estos últimos dias en tu idea, y llegue a una conclusión que vas a tener que sobreescribirlo vos en PAWN, como un simple calculo...
No es sencillo pero tampoco dificil de comprender el calculo.
Tomas el angulo del screen del player, y refiriendo al de YAW.
Si no recuerdo mal era Pitch, Yaw, y Roll, por lo tanto el de la posicion '1' en el vector asociado al angulo, es Yaw.
PHP Code:
enum AXIS
{
PITCH = 0,
YAW,
ROLL
};
new AXIS:Vector[ 3 ];
Luego de tomarlos los últimos angulos verificar cada uno de ellos, por lo tanto debes de pasar sus valores a un valor absoluto, ¿Que me refiero con esto?
Si tengo un angulo obtenido en el CS el cual su valor es:
-90º => | ( -90º ) | = 270º.
Por lo tanto uno ves que se obtuvo dicho valor, pasamos a calculos su valor en radianes.
Rad = Deg * ( K.pi / 180 );
Español:
Radianes = Grados * ( pi / 180 );
Una ves que obtuvistes dicho valor en radianes puedes verificar los diferentes puntos mediante un simple if x1 == x2, claro que estariamos pasando una linea de consumo, supongo que es infima, ya que el unico valor que recorremos y verificamos son valores con coma flotante o decimales, como les quieras llamar.
Te dejo un lindo dibujo:
[IMG]http://img404.**************/img404/4194/superimagensenusradian.jpg[/IMG]
Edit:
Te sigo dejando datos...
Para obtener el valor absoluto del angulo que se presente en un valor negativo:
PHP Code:
stock absolute_degree( &Float:fAngle )
{
fAngle = fAngle < 0 ? ( 360.0 + fAngle ) : fAngle;
}
Edit2:
Te dejo el plugin que estuve desarrollando hasta ahora, sirve, lo unico es que esta adaptado para funcionar correctamente si el giro se hace hacia la izquierda, hacia la derecha habria que cambiar unas lineas.
PHP Code:
/* Plugin generated by AMXX-Studio */
#include <amxmodx>
#include <amxmisc>
#include <fakemeta>
#define PLUGIN "Detectar Giro 360º Izquierda"
#define VERSION "1.0"
#define AUTHOR "fearAR"
//#define SET_USER_ANGLES
new Float:fViewAngles[ 33 ][ 3 ], Float:fGameTime[ 33 ], iInit[ 33 ];
new Float:g_fViewAngles[ 33 ][ 3 ];
#define MAX_POINT_RADIANS 5
#define MAX_TIME 0.5
new const Float:fValores[ MAX_POINT_RADIANS ] =
{
0.0,
1.57,
3.14,
4.71,
0.0
};
public plugin_init() {
register_plugin(PLUGIN, VERSION, AUTHOR)
register_clcmd( "say iniciar", "function_init" );
register_forward( FM_PlayerPostThink, "fw_PlayerPostThink" );
}
public client_putinserver( id )
{
iInit[ id ] = 0;
}
public function_init( id )
{
if( !is_user_alive( id ) || iInit[ id ] ) return PLUGIN_HANDLED;
pev( id, pev_angles, fViewAngles[ id ] );
absolute_degree( fViewAngles[ id ][ 1 ] );
fGameTime[ id ] = get_gametime();
iInit[ id ] = 1;
client_print( id, print_chat, "Empezo..." );
return PLUGIN_HANDLED;
}
public fw_PlayerPostThink( id )
{
if ( !( 1 <= id <= 32 ) || !is_user_alive( id ) ) return FMRES_IGNORED;
if ( !iInit[ id ] ) return FMRES_IGNORED;
if ( get_gametime() > ( fGameTime[ id ] + MAX_TIME ) )
{
client_print( id, print_chat, "Termino..." );
iInit[ id ] = 0;
return FMRES_IGNORED;
}
else
{
pev( id, pev_angles, g_fViewAngles[ id ] );
absolute_degree( g_fViewAngles[ id ][ 1 ] );
g_fViewAngles[ id ][ 1 ] = floatsub( g_fViewAngles[ id ][ 1 ], fViewAngles[ id ][ 1 ] );
absolute_degree( g_fViewAngles[ id ][ 1 ] );
degrees_to_radian( g_fViewAngles[ id ][ 1 ], g_fViewAngles[ id ][ 1 ] );
if ( compare_floats( g_fViewAngles[ id ][ 1 ], fValores[ iInit[ id ] ] ) && iInit[ id ] )
{
client_print( id, print_chat, "Radianes pasados: %.2f", g_fViewAngles[ id ][ 1 ] );
fGameTime[ id ] = get_gametime();
if ( ++iInit[ id ] == ( sizeof fValores ) )
{
iInit[ id ] = 0;
client_print( id, print_chat, "Distes una vuelta!" );
#if defined SET_USER_ANGLES
new parm[ 4 ];
parm[ 0 ] = id;
parm[ 1 ] = floatround( fViewAngles[ id ][ 0 ] );
parm[ 2 ] = floatround( fViewAngles[ id ][ 1 ] );
parm[ 3 ] = floatround( fViewAngles[ id ][ 2 ] );
set_task( 1.0, "setAngles", _, parm, sizeof parm );
#endif
}
}
}
return FMRES_IGNORED;
}
public setAngles( parm[ 4 ] )
{
static id;
id = parm[ 0 ];
new Float:fAngles[ 3 ];
for( new i = 0; i < sizeof fAngles; i++ )
fAngles[ i ] = float( parm[ i + 1 ] );
set_pev( id, pev_v_angle, fAngles );
set_pev( id, pev_angles, fAngles );
set_pev( id, pev_fixangle, 1 );
}
stock absolute_degree( &Float:fAngle )
{
fAngle = fAngle < 0 ? ( 360.0 + fAngle ) : fAngle;
}
stock degrees_to_radian( Float:fIn, &Float:fOut )
fOut = floatmul( fIn, floatdiv( 3.14159264, 180.0 ) );
stock radian_to_degrees( Float:fIn, &Float:fOut )
fOut = floatmul( fIn, floatdiv( 180.0, 3.14159264 ) );
stock compare_floats( Float:fIn1, Float:fIn2 )
{
static Float:valor;
valor = floatsub( fIn1, fIn2 );
valor = valor < 0.0 ? floatmul( valor, -1.0 ) : valor;
if( valor < 0.1) return 1
return 0
}
Edit3:
Detecta hacia los 2 lados, cuanto menor sea el tiempo aceptable para llegar a cada valor del vector fValores, es menos propenso a errores.
PHP Code:
/* Plugin generated by AMXX-Studio */
#include <amxmodx>
#include <amxmisc>
#include <fakemeta>
#define PLUGIN "Detectar Giro 360º Izquierda"
#define VERSION "1.0"
#define AUTHOR "fearAR"
//#define SET_USER_ANGLES
enum MAX_DIRECCIONES
{
LEFT = 0,
RIGHT
};
new Float:fViewAngles[ 33 ][ 3 ], Float:fGameTime[ 33 ], Float:g_fViewAngles[ 33 ][ 3 ], Float:fGameTime2[ 33 ];
new iInit[ 33 ], MAX_DIRECCIONES:g_iDirection[ 33 ];
#define MAX_POINT_RADIANS 5
#define MAX_TIME 0.2
new const Float:fValores[ MAX_POINT_RADIANS ] =
{
0.0,
1.57,
3.14,
4.71,
0.0
};
public plugin_init() {
register_plugin(PLUGIN, VERSION, AUTHOR)
register_clcmd( "say iniciar", "function_init" );
register_forward( FM_PlayerPostThink, "fw_PlayerPostThink" );
}
public client_putinserver( id )
{
iInit[ id ] = -1;
g_iDirection[ id ] = LEFT;
fGameTime2[ id ] = get_gametime();
}
public function_init( id )
{
if( !is_user_alive( id ) || iInit[ id ] >= 0 ) return PLUGIN_HANDLED;
pev( id, pev_angles, fViewAngles[ id ] );
absolute_degree( fViewAngles[ id ][ 1 ] );
g_iDirection[ id ] = LEFT;
fGameTime[ id ] = get_gametime();
fGameTime2[ id ] = get_gametime();
iInit[ id ] = 1;
client_print( id, print_chat, "Empezo..." );
return PLUGIN_HANDLED;
}
public fw_PlayerPostThink( id )
{
if ( !( 1 <= id <= 32 ) || !is_user_alive( id ) ) return FMRES_IGNORED;
if ( iInit[ id ] < 0 ) return FMRES_IGNORED;
if ( get_gametime() > ( fGameTime[ id ] + MAX_TIME ) )
{
client_print( id, print_chat, "Termino..." );
iInit[ id ] = -1;
return FMRES_IGNORED;
}
else
{
pev( id, pev_angles, g_fViewAngles[ id ] );
absolute_degree( g_fViewAngles[ id ][ 1 ] );
g_fViewAngles[ id ][ 1 ] = floatsub( g_fViewAngles[ id ][ 1 ], fViewAngles[ id ][ 1 ] );
absolute_degree( g_fViewAngles[ id ][ 1 ] );
degrees_to_radian( g_fViewAngles[ id ][ 1 ], g_fViewAngles[ id ][ 1 ] );
if ( iInit[ id ] == 1 && compare_floats( g_fViewAngles[ id ][ 1 ], fValores[ sizeof fValores - 2 ] ) ) {
iInit[ id ] = 3;
g_iDirection[ id ] = RIGHT;
}
if ( get_gametime() >= ( fGameTime2[ id ] + 0.2 ) )
{
client_print( id, print_chat, "%.2f", g_fViewAngles[ id ][ 1 ] );
fGameTime2[ id ] = get_gametime();
}
if ( compare_floats( g_fViewAngles[ id ][ 1 ], fValores[ iInit[ id ] ] ) && iInit[ id ] >= 0 )
{
client_print( id, print_chat, "Radianes pasados: %.2f", g_fViewAngles[ id ][ 1 ] );
iInit[ id ] += g_iDirection[ id ] == LEFT ? 1 : 0;
if ( ( g_iDirection[ id ] == LEFT && iInit[ id ] >= ( sizeof fValores ) ) ||
( g_iDirection[ id ] == RIGHT && iInit[ id ] <= 0 ) )
{
iInit[ id ] = -1;
client_print( id, print_chat, "Distes una vuelta!" );
#if defined SET_USER_ANGLES
new parm[ 4 ];
parm[ 0 ] = id;
parm[ 1 ] = floatround( fViewAngles[ id ][ 0 ] );
parm[ 2 ] = floatround( fViewAngles[ id ][ 1 ] );
parm[ 3 ] = floatround( fViewAngles[ id ][ 2 ] );
set_task( 1.0, "setAngles", _, parm, sizeof parm );
#endif
}
iInit[ id ] += g_iDirection[ id ] == RIGHT ? -1 : 0;
fGameTime[ id ] = get_gametime();
}
}
return FMRES_IGNORED;
}
public setAngles( parm[ 4 ] )
{
static id;
id = parm[ 0 ];
new Float:fAngles[ 3 ];
for( new i = 0; i < sizeof fAngles; i++ )
fAngles[ i ] = float( parm[ i + 1 ] );
set_pev( id, pev_v_angle, fAngles );
set_pev( id, pev_angles, fAngles );
set_pev( id, pev_fixangle, 1 );
}
stock absolute_degree( &Float:fAngle )
{
fAngle = fAngle < 0 ? ( 360.0 + fAngle ) : fAngle;
}
stock degrees_to_radian( Float:fIn, &Float:fOut )
fOut = floatmul( fIn, floatdiv( 3.14159264, 180.0 ) );
stock radian_to_degrees( Float:fIn, &Float:fOut )
fOut = floatmul( fIn, floatdiv( 180.0, 3.14159264 ) );
stock compare_floats( Float:fIn1, Float:fIn2 )
{
static Float:valor;
valor = floatsub( fIn1, fIn2 );
valor = valor < 0.0 ? floatmul( valor, -1.0 ) : valor;
if( valor < 0.1) return 1
return 0
}
Saludos.
__________________