Veteran Member
11-06-2021
, 16:42
Entity rotation around an arbitrary axis
#1
I Have a drone i want to rotate the drone depending on the drone forward or right axis for example when holding space(IN_JUMP) or ctrl(IN_DUCK) i want the drone to raise up/down ( rotation around the right axis of the drone ) and when holding a(IN_RIGHT) or d(IN_LEFT) to rotate around the forward access of the drone.
I've tried using the rotation matrix method but sadly failed due not knowing what i am really doing.
what i've tried.
TEST CODE
Spoiler
PHP Code:
case DRONE_CONTROL :
{
static Float : fAngle [ 2 ];
fAngle [ 0 ] = entity_get_float ( ent , DRONE_ROTATION_UPWARDS );
fAngle [ 1 ] = entity_get_float ( ent , DRONE_ROTATION_SIDEWAY );
if( iButtons & IN_FORWARD )
{
entity_set_float ( ent , EV_FL_speed , ( fSpeed = floatmin ( fSpeed + 10.0 , fMaxSpeed )));
}
else if( iButtons & IN_BACK )
{
entity_set_float ( ent , EV_FL_speed , ( fSpeed = floatmax ( fSpeed - 10.0 , 0.0 )));
}
if( fSpeed > 0.0 )
{
angle_vector ( fvAngles , ANGLEVECTOR_FORWARD , fVector );
xs_vec_mul_scalar ( fVector , fSpeed , fVelocity );
//xs_vec_add(fVelocity, fVelocity, fVelocity);
}
if( iButtons & IN_MOVERIGHT || iButtons & IN_RIGHT )
{
fAngle [ 1 ] += 5.0 ;
if( fAngle [ 1 ] > 360.0 ) fAngle [ 1 ] -= 360.0 ;
entity_set_float ( ent , DRONE_ROTATION_SIDEWAY , fAngle [ 1 ]);
angle_vector ( fvAngles , ANGLEVECTOR_UP , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 255 , 255 , 0 })
rotate_3dvector ( fVector , 0.0 , 0.0 , fAngle [ 1 ], fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 255 , 0 , 0 })
vector_to_angle ( fVector , fvAngles );
}
else if( iButtons & IN_MOVELEFT || iButtons & IN_LEFT )
{
fAngle [ 1 ] -= 5.0 ;
if( fAngle [ 1 ] < 0.0 ) fAngle [ 1 ] += 360.0 ;
entity_set_float ( ent , DRONE_ROTATION_SIDEWAY , fAngle [ 1 ]);
angle_vector ( fvAngles , ANGLEVECTOR_UP , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 255 , 255 , 0 })
rotate_3dvector ( fVector , 0.0 , 0.0 , fAngle [ 1 ], fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 255 , 0 , 0 })
vector_to_angle ( fVector , fvAngles );
}
else if( iButtons & IN_JUMP )
{
fAngle [ 0 ] += 5.0 ;
if( fAngle [ 0 ] > 360.0 ) fAngle [ 0 ] -= 360.0 ;
entity_set_float ( ent , DRONE_ROTATION_UPWARDS , fAngle [ 0 ]);
angle_vector ( fvAngles , ANGLEVECTOR_FORWARD , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 0 , 0 , 255 })
rotate_3dvector ( fVector , 0.0 , fAngle [ 0 ], 0.0 , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 0 , 255 , 255 })
vector_to_angle ( fVector , fvAngles );
}
else if( iButtons & IN_DUCK )
{
fAngle [ 0 ] -= 5.0 ;
if( fAngle [ 0 ] < 0.0 ) fAngle [ 0 ] += 360.0 ;
entity_set_float ( ent , DRONE_ROTATION_UPWARDS , fAngle [ 0 ]);
angle_vector ( fvAngles , ANGLEVECTOR_FORWARD , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 0 , 0 , 255 })
rotate_3dvector ( fVector , 0.0 , fAngle [ 0 ], 0.0 , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 0 , 255 , 255 })
vector_to_angle ( fVector , fvAngles );
}
// lets make sure the plane doesn't exceed the maximum speed limits.
if( xs_vec_len ( fVelocity ) > fMaxSpeed )
{
xs_vec_normalize ( fVelocity , fVelocity );
xs_vec_mul_scalar ( fVelocity , fMaxSpeed , fVelocity );
}
fVelocity [ 2 ] *= - 1.0 ;
entity_set_vector ( ent , EV_VEC_angles , fvAngles );
entity_set_vector ( ent , EV_VEC_velocity , fVelocity );
entity_set_float ( ent , EV_FL_nextthink , get_gametime () + 0.1 );
}
................
stock rotate_3dvector ( Float : fInput_Vector [ 3 ], Float : fAngleX = 0.0 , Float : fAngleY = 0.0 , Float : fAngleZ = 0.0 , Float : fOutput_Vector [ 3 ])
{
static Float : fMatrix [ 3 ][ 3 ];
fMatrix [ 0 ][ 0 ] = floatcos ( fAngleX , degrees ) * floatcos ( fAngleY , degrees );
fMatrix [ 0 ][ 1 ] = floatcos ( fAngleX , degrees ) * floatsin ( fAngleY , degrees ) * floatsin ( fAngleZ , degrees ) - floatsin ( fAngleX , degrees ) * floatcos ( fAngleZ , degrees );
fMatrix [ 0 ][ 2 ] = floatcos ( fAngleX , degrees ) * floatsin ( fAngleY , degrees ) * floatcos ( fAngleZ , degrees ) + floatsin ( fAngleX , degrees ) * floatsin ( fAngleZ , degrees );
fMatrix [ 1 ][ 0 ] = floatsin ( fAngleX , degrees ) * floatcos ( fAngleY , degrees );
fMatrix [ 1 ][ 1 ] = floatsin ( fAngleX , degrees ) * floatsin ( fAngleY , degrees ) * floatsin ( fAngleZ , degrees ) + floatcos ( fAngleX , degrees ) * floatcos ( fAngleZ , degrees );
fMatrix [ 1 ][ 2 ] = floatsin ( fAngleX , degrees ) * floatsin ( fAngleY , degrees ) * floatcos ( fAngleZ , degrees ) - floatcos ( fAngleX , degrees ) * floatsin ( fAngleZ , degrees );
fMatrix [ 2 ][ 0 ] = - floatsin ( fAngleY , degrees );
fMatrix [ 2 ][ 1 ] = floatcos ( fAngleY , degrees ) * floatsin ( fAngleZ , degrees );
fMatrix [ 2 ][ 2 ] = floatcos ( fAngleY , degrees ) * floatcos ( fAngleZ , degrees );
for(new i = 0 ; i < 3 ; i ++)
{
fOutput_Vector [ i ] = ( fInput_Vector [ 0 ] * fMatrix [ i ][ 0 ]) + ( fInput_Vector [ 1 ] * fMatrix [ i ][ 1 ]) + ( fInput_Vector [ 2 ] * fMatrix [ i ][ 2 ])
}
}
stock fm_draw_line ( id , Float : x1 , Float : y1 , Float : z1 , Float : x2 , Float : y2 , Float : z2 , g_iColor [ 3 ])
{
message_begin ( id ? MSG_ONE_UNRELIABLE : MSG_BROADCAST , SVC_TEMPENTITY , _ , id ? id : 0 )
write_byte ( TE_BEAMPOINTS )
write_coord ( floatround ( x1 ))
write_coord ( floatround ( y1 ))
write_coord ( floatround ( z1 ))
write_coord ( floatround ( x2 ))
write_coord ( floatround ( y2 ))
write_coord ( floatround ( z2 ))
write_short ( g_iTrailSprite )
write_byte ( 1 ) // frame
write_byte ( 10 ) // framestart
write_byte ( 10 ) // life
write_byte ( 30 )
write_byte ( 0 )
write_byte ( g_iColor [ 0 ])
write_byte ( g_iColor [ 1 ])
write_byte ( g_iColor [ 2 ])
write_byte ( 200 )
write_byte ( 0 )
message_end ()
}
FULL CODE
Spoiler
PHP Code:
/* Plugin generated by AMXX-Studio */
#include <amxmodx>
#include <fakemeta>
#include <engine>
#include <xs>
#include <jailbreak_core>
#include <hamsandwich>
#define PLUGIN "[JB] SHOP: Drone"
#define AUTHOR "Natsheh"
#define DRONE_OWNER EV_INT_iuser3
#define DRONE_CURRENT_STATUS EV_INT_iuser4
#define DRONE_ROTATION_SIDEWAY EV_FL_fuser4
#define DRONE_ROTATION_UPWARDS EV_FL_fuser3
#define DRONE_CAMERA pev_iuser2
#define CRASH_SPEED 200.0
new const drone_entity_classname [] = "Drone"
new const drone_entity_oldclassname [] = "info_target"
enum _ : DRONE_STATUS (+= 1 )
{
DRONE_STANDBY = 0 ,
DRONE_CONTROL ,
DRONE_KILL
}
enum _ : DRONE_CVARS (+= 1 )
{
CVAR_DRONE_SPEED = 0 ,
CVAR_DRONE_GRAVITY ,
CVAR_DRONE_HEALTH
}
new const szCvars_data [][][] = {
{ "jb_drone_speed" , "400.0" },
{ "jb_drone_gravity" , "0.8" },
{ "jb_drone_health" , "300.0" }
}
new _ : g_iCvars [ DRONE_CVARS ], boom , smoke , g_iTrailSprite , g_itemid , g_user_drone [ 33 ], DRONE_MODEL [ 64 ] = "models/jailbreak/drone.mdl" ;
public plugin_precache ()
{
smoke = precache_model ( "sprites/smoke.spr" )
boom = precache_model ( "sprites/zerogxplode.spr" )
g_iTrailSprite = precache_model ( "sprites/laserbeam.spr" )
jb_ini_get_keyvalue ( "DRONE" , "DRONE_MODEL" , DRONE_MODEL , charsmax ( DRONE_MODEL ))
precache_model ( DRONE_MODEL );
}
public plugin_init ()
{
register_plugin ( PLUGIN , VERSION , AUTHOR )
g_itemid = register_jailbreak_shopitem ( "Drone" , "a flying drone" , 25000 , TEAM_GUARDS );
register_think ( drone_entity_classname , "fw_drone_brain" );
register_touch ( drone_entity_classname , "worldspawn" , "fw_drone_touch" );
RegisterHam ( Ham_Think , "trigger_camera" , "Camera_Think" )
RegisterHam ( Ham_Killed , drone_entity_oldclassname , "fw_drone_killed_post" , 1 );
for(new i ; i < sizeof szCvars_data ; i ++)
{
g_iCvars [ i ] = register_cvar ( szCvars_data [ i ][ 0 ], szCvars_data [ i ][ 1 ]);
}
//RegisterHam(Ham_ObjectCaps, drone_entity_oldclassname, "drone_objectcaps_pre");
//RegisterHam(Ham_Use, drone_entity_oldclassname, "drone_use_pre");
register_clcmd ( "drop" , "clcmd_drop" );
}
public clcmd_drop ( id )
{
if( g_user_drone [ id ] > 0 )
{
new ent = g_user_drone [ id ];
if( pev_valid ( ent ))
entity_set_int ( ent , DRONE_CURRENT_STATUS , DRONE_STANDBY );
attach_view ( id , id );
g_user_drone [ id ] = 0 ;
return 1 ;
}
return 0 ;
}
public fw_drone_touch ( ent , toucher )
{
if( pev_valid ( ent ))
{
static Float : fVelocity [ 3 ];
entity_get_vector ( ent , EV_VEC_velocity , fVelocity );
if( xs_vec_len ( fVelocity ) >= CRASH_SPEED )
{
ExecuteHamB ( Ham_TakeDamage , ent , toucher , toucher , 25.0 , DMG_CRUSH );
}
}
}
public fw_drone_killed_post ( victim , attacker , gib )
{
new classname [ 16 ];
entity_get_string ( victim , EV_SZ_classname , classname , charsmax ( classname ))
if(! equal ( drone_entity_classname , classname )) return HAM_IGNORED ;
new Float : fOrigin [ 3 ];
pev ( victim , pev_origin , fOrigin );
message_begin ( MSG_BROADCAST , SVC_TEMPENTITY )
write_byte ( TE_EXPLOSION )
write_coord ( floatround ( fOrigin [ 0 ]))
write_coord ( floatround ( fOrigin [ 1 ]))
write_coord ( floatround ( fOrigin [ 2 ]))
write_short ( boom )
write_byte ( 50 )
write_byte ( 15 )
write_byte ( 0 )
message_end ()
if( pev_valid ( victim ))
{
new id = entity_get_int ( victim , DRONE_OWNER );
attach_view ( id , id );
g_user_drone [ id ] = 0 ;
}
return HAM_IGNORED ;
}
public drone_use_pre ( id , caller , activator , use_type , Float : value )
{
new classname [ 16 ];
entity_get_string ( id , EV_SZ_classname , classname , charsmax ( classname ))
cprint_chat ( 0 , _ , "%s = %s" , classname , drone_entity_classname );
if(! equal ( drone_entity_classname , classname )) return HAM_IGNORED ;
attach_drone_player ( caller , id )
return HAM_SUPERCEDE ;
}
attach_drone_player ( iOwner , ent )
{
entity_set_int ( ent , DRONE_CURRENT_STATUS , DRONE_CONTROL );
new ent2 = pev ( ent , DRONE_CAMERA );
if( ent2 > 0 ) ExecuteHam ( Ham_Use , ent2 , iOwner , iOwner , USE_TOGGLE , 1.0 )
g_user_drone [ iOwner ] = ent ;
set_pev ( iOwner , pev_maxspeed , - 1.0 );
cprint_chat ( iOwner , _ , "You're driving the drone remotely!" );
}
public drone_objectcaps_pre ( id )
{
new classname [ 16 ];
entity_get_string ( id , EV_SZ_classname , classname , charsmax ( classname ))
if(! equal ( drone_entity_classname , classname )) return HAM_IGNORED ;
SetHamReturnInteger ( FCAP_IMPULSE_USE );
return HAM_SUPERCEDE ;
}
public jb_shop_item_bought ( id , itemid )
{
if( itemid == g_itemid )
{
new ent = create_entity ( "info_target" );
if(! ent ) return;
new Float : fSpawnOrigin [ 3 ], Float : fTemp [ 3 ];
velocity_by_aim ( id , 100 , fTemp );
fTemp [ 2 ] = 0.0 ;
entity_get_vector ( id , EV_VEC_origin , fSpawnOrigin );
xs_vec_add ( fSpawnOrigin , fTemp , fSpawnOrigin );
entity_set_string ( ent , EV_SZ_classname , drone_entity_classname );
entity_set_vector ( ent , EV_VEC_origin , fSpawnOrigin );
entity_set_model ( ent , DRONE_MODEL );
entity_set_size ( ent , Float :{- 3.0 ,- 3.0 ,- 3.0 }, Float :{ 3.0 , 3.0 , 3.0 });
entity_set_float ( ent , EV_FL_takedamage , DAMAGE_YES );
entity_set_float ( ent , EV_FL_health , get_pcvar_float ( g_iCvars [ CVAR_DRONE_HEALTH ]));
entity_set_int ( ent , EV_INT_solid , SOLID_BBOX );
entity_set_int ( ent , EV_INT_movetype , MOVETYPE_FLY );
entity_set_float ( ent , EV_FL_maxspeed , get_pcvar_float ( g_iCvars [ CVAR_DRONE_SPEED ]));
set_pev ( ent , pev_controller_0 , 125 );
entity_set_int ( ent , DRONE_CURRENT_STATUS , DRONE_STANDBY );
entity_set_int ( ent , DRONE_OWNER , id );
entity_set_float ( ent , EV_FL_nextthink , get_gametime () + 0.01 );
static iszTriggerCamera
if( ! iszTriggerCamera )
{
iszTriggerCamera = engfunc ( EngFunc_AllocString , "trigger_camera" )
}
new iEnt = engfunc ( EngFunc_CreateNamedEntity , iszTriggerCamera );
if( iEnt > 0 )
{
set_pev ( iEnt , pev_globalname , "drone_camera" );
set_kvd ( 0 , KV_ClassName , "trigger_camera" )
set_kvd ( 0 , KV_fHandled , 0 )
set_kvd ( 0 , KV_KeyName , "wait" )
set_kvd ( 0 , KV_Value , "999999" )
dllfunc ( DLLFunc_KeyValue , iEnt , 0 )
set_pev ( iEnt , pev_spawnflags , SF_CAMERA_PLAYER_TARGET | SF_CAMERA_PLAYER_POSITION )
set_pev ( iEnt , pev_flags , pev ( iEnt , pev_flags ) | FL_ALWAYSTHINK )
dllfunc ( DLLFunc_Spawn , iEnt )
// }
set_pev ( ent , DRONE_CAMERA , iEnt );
set_pev ( iEnt , pev_owner , ent );
entity_set_edict ( ent , EV_ENT_owner , iEnt );
attach_drone_player ( id , ent )
}
}
}
public Camera_Think ( iEnt )
{
static szGlobalname [ 32 ];
pev ( iEnt , pev_globalname , szGlobalname , charsmax ( szGlobalname ))
if(! equal ( szGlobalname , "drone_camera" )) return ;
static Float : fVecPlayerOrigin [ 3 ], Float : fVecCameraOrigin [ 3 ], Float : fVecAngles [ 3 ], Float : fVec [ 3 ], id ;
id = pev ( iEnt , pev_owner );
if(! pev_valid ( id ))
{
set_pev ( iEnt , pev_flags , FL_KILLME );
return;
}
pev ( id , pev_origin , fVecPlayerOrigin )
pev ( id , pev_angles , fVecAngles )
angle_vector ( fVecAngles , ANGLEVECTOR_FORWARD , fVec );
static Float : units ; units = - 50.0 ;
//Move back/forward to see ourself
fVecCameraOrigin [ 0 ] = fVecPlayerOrigin [ 0 ] + ( fVec [ 0 ] * units )
fVecCameraOrigin [ 1 ] = fVecPlayerOrigin [ 1 ] + ( fVec [ 1 ] * units )
fVecCameraOrigin [ 2 ] = fVecPlayerOrigin [ 2 ] + ( fVec [ 2 ] * units ) + 5.0
static tr2 ; tr2 = create_tr2 ();
engfunc ( EngFunc_TraceLine , fVecPlayerOrigin , fVecCameraOrigin , IGNORE_MONSTERS , id , tr2 )
static Float : flFraction
get_tr2 ( tr2 , TR_flFraction , flFraction )
if( flFraction != 1.0 ) // adjust camera place if close to a wall
{
flFraction *= units ;
fVecCameraOrigin [ 0 ] = fVecPlayerOrigin [ 0 ] + ( fVec [ 0 ] * flFraction );
fVecCameraOrigin [ 1 ] = fVecPlayerOrigin [ 1 ] + ( fVec [ 1 ] * flFraction );
fVecCameraOrigin [ 2 ] = fVecPlayerOrigin [ 2 ] + ( fVec [ 2 ] * flFraction );
}
fVecAngles [ 0 ] *= - 1 ;
set_pev ( iEnt , pev_origin , fVecCameraOrigin );
set_pev ( iEnt , pev_angles , fVecAngles );
free_tr2 ( tr2 );
}
#define Cosine(%1) floatcos(%1,degrees)
#define Sine(%1) floatsin(%1,degrees)
#define SquareRoot(%1) floatsqroot(%1)
public fw_drone_brain ( ent )
{
static iOwner ;
iOwner = entity_get_int ( ent , DRONE_OWNER );
static iButtons , Float : fOrigin [ 3 ], Float : fvAngles [ 3 ], Float : fVector [ 3 ], Float : fVelocity [ 3 ] = { 0.0 , 0.0 , 0.0 }, Float : fSpeed , Float : fMaxSpeed ;
fMaxSpeed = entity_get_float ( ent , EV_FL_maxspeed );
fSpeed = entity_get_float ( ent , EV_FL_speed );
iButtons = get_user_button ( iOwner );
entity_get_vector ( ent , EV_VEC_velocity , fVelocity );
entity_get_vector ( ent , EV_VEC_angles , fvAngles );
entity_get_vector ( ent , EV_VEC_origin , fOrigin );
if( xs_vec_len ( fVelocity ) > 0.0 )
{
message_begin ( MSG_BROADCAST , SVC_TEMPENTITY )
write_byte ( 22 )
write_short ( ent )
write_short ( smoke )
write_byte ( 1 )
write_byte ( 10 )
write_byte ( 200 )
write_byte ( 200 )
write_byte ( 200 )
write_byte ( 128 )
message_end ()
set_pev ( ent , pev_frame , 1 );
set_pev ( ent , pev_framerate , 1.0 );
}
else
{
set_pev ( ent , pev_frame , 0 );
set_pev ( ent , pev_framerate , 0.0 );
}
switch( entity_get_int ( ent , DRONE_CURRENT_STATUS ) )
{
case DRONE_STANDBY :
{
static target ;
get_user_aiming ( iOwner , target )
if( target == ent && iButtons & IN_USE && !( pev ( iOwner , pev_oldbuttons ) & IN_USE ))
{
attach_drone_player ( iOwner , ent );
}
entity_set_float ( ent , EV_FL_nextthink , get_gametime () + 0.01 );
}
case DRONE_CONTROL :
{
static Float : fAngle [ 2 ];
fAngle [ 0 ] = entity_get_float ( ent , DRONE_ROTATION_UPWARDS );
fAngle [ 1 ] = entity_get_float ( ent , DRONE_ROTATION_SIDEWAY );
if( iButtons & IN_FORWARD )
{
entity_set_float ( ent , EV_FL_speed , ( fSpeed = floatmin ( fSpeed + 10.0 , fMaxSpeed )));
}
else if( iButtons & IN_BACK )
{
entity_set_float ( ent , EV_FL_speed , ( fSpeed = floatmax ( fSpeed - 10.0 , 0.0 )));
}
if( fSpeed > 0.0 )
{
angle_vector ( fvAngles , ANGLEVECTOR_FORWARD , fVector );
xs_vec_mul_scalar ( fVector , fSpeed , fVelocity );
//xs_vec_add(fVelocity, fVelocity, fVelocity);
}
if( iButtons & IN_MOVERIGHT || iButtons & IN_RIGHT )
{
fAngle [ 1 ] += 5.0 ;
if( fAngle [ 1 ] > 360.0 ) fAngle [ 1 ] -= 360.0 ;
entity_set_float ( ent , DRONE_ROTATION_SIDEWAY , fAngle [ 1 ]);
angle_vector ( fvAngles , ANGLEVECTOR_UP , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 255 , 255 , 0 })
rotate_3dvector ( fVector , 0.0 , 0.0 , fAngle [ 1 ], fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 255 , 0 , 0 })
vector_to_angle ( fVector , fvAngles );
}
else if( iButtons & IN_MOVELEFT || iButtons & IN_LEFT )
{
fAngle [ 1 ] -= 5.0 ;
if( fAngle [ 1 ] < 0.0 ) fAngle [ 1 ] += 360.0 ;
entity_set_float ( ent , DRONE_ROTATION_SIDEWAY , fAngle [ 1 ]);
angle_vector ( fvAngles , ANGLEVECTOR_UP , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 255 , 255 , 0 })
rotate_3dvector ( fVector , 0.0 , 0.0 , fAngle [ 1 ], fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 255 , 0 , 0 })
vector_to_angle ( fVector , fvAngles );
}
else if( iButtons & IN_JUMP )
{
fAngle [ 0 ] += 5.0 ;
if( fAngle [ 0 ] > 360.0 ) fAngle [ 0 ] -= 360.0 ;
entity_set_float ( ent , DRONE_ROTATION_UPWARDS , fAngle [ 0 ]);
angle_vector ( fvAngles , ANGLEVECTOR_FORWARD , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 0 , 0 , 255 })
rotate_3dvector ( fVector , 0.0 , fAngle [ 0 ], 0.0 , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 0 , 255 , 255 })
vector_to_angle ( fVector , fvAngles );
}
else if( iButtons & IN_DUCK )
{
fAngle [ 0 ] -= 5.0 ;
if( fAngle [ 0 ] < 0.0 ) fAngle [ 0 ] += 360.0 ;
entity_set_float ( ent , DRONE_ROTATION_UPWARDS , fAngle [ 0 ]);
angle_vector ( fvAngles , ANGLEVECTOR_FORWARD , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 0 , 0 , 255 })
rotate_3dvector ( fVector , 0.0 , fAngle [ 0 ], 0.0 , fVector );
fm_draw_line ( iOwner , fVector [ 0 ], fVector [ 1 ], fVector [ 2 ], fVector [ 0 ]* 50.0 , fVector [ 1 ]* 50.0 , fVector [ 2 ]* 50.0 , { 0 , 255 , 255 })
vector_to_angle ( fVector , fvAngles );
}
// lets make sure the plane doesn't exceed the maximum speed limits.
if( xs_vec_len ( fVelocity ) > fMaxSpeed )
{
xs_vec_normalize ( fVelocity , fVelocity );
xs_vec_mul_scalar ( fVelocity , fMaxSpeed , fVelocity );
}
fVelocity [ 2 ] *= - 1.0 ;
entity_set_vector ( ent , EV_VEC_angles , fvAngles );
entity_set_vector ( ent , EV_VEC_velocity , fVelocity );
entity_set_float ( ent , EV_FL_nextthink , get_gametime () + 0.1 );
}
case DRONE_KILL :
{
// more stuff to think about
}
}
}
// thanks to alka
stock SetupMatrix ( Float : angle , Float : vector [ 3 ], Float : rotation [ 4 ][ 4 ], Float : point [ 3 ])
{
new Float : L = ( vector [ 0 ] * vector [ 0 ] + vector [ 1 ] * vector [ 1 ] + vector [ 2 ] * vector [ 2 ]);
//angle = angle * M_PI / 180.0;
new Float : u2 = vector [ 0 ] * vector [ 0 ];
new Float : v2 = vector [ 1 ] * vector [ 1 ];
new Float : w2 = vector [ 2 ] * vector [ 2 ];
rotation [ 0 ][ 0 ] = ( u2 + ( v2 + w2 ) * Cosine ( angle )) / L ;
rotation [ 0 ][ 1 ] = ( vector [ 0 ] * vector [ 1 ] * ( 1 - Cosine ( angle )) - vector [ 2 ] * SquareRoot ( L ) * Sine ( angle )) / L ;
rotation [ 0 ][ 2 ] = ( vector [ 0 ] * vector [ 2 ] * ( 1 - Cosine ( angle )) + vector [ 1 ] * SquareRoot ( L ) * Sine ( angle )) / L ;
rotation [ 0 ][ 3 ] = (( point [ 0 ] * ( v2 + w2 ) - vector [ 0 ] * ( point [ 1 ] * vector [ 1 ] + point [ 2 ] * vector [ 2 ])) * ( 1 - Cosine ( angle )) + ( point [ 1 ] * vector [ 2 ] - point [ 2 ] * vector [ 1 ]) * SquareRoot ( L ) * Sine ( angle )) / L ;
rotation [ 1 ][ 0 ] = ( vector [ 0 ] * vector [ 1 ] * ( 1 - Cosine ( angle )) + vector [ 2 ] * SquareRoot ( L ) * Sine ( angle )) / L ;
rotation [ 1 ][ 1 ] = ( v2 + ( u2 + w2 ) * Cosine ( angle )) / L ;
rotation [ 1 ][ 2 ] = ( vector [ 1 ] * vector [ 2 ] * ( 1 - Cosine ( angle )) - vector [ 0 ] * SquareRoot ( L ) * Sine ( angle )) / L ;
rotation [ 1 ][ 3 ] = (( point [ 1 ] * ( u2 + w2 ) - vector [ 1 ] * ( point [ 0 ] * vector [ 0 ] + point [ 2 ] * vector [ 2 ])) * ( 1 - Cosine ( angle )) + ( point [ 2 ] * vector [ 0 ] - point [ 0 ] * vector [ 2 ]) * SquareRoot ( L ) * Sine ( angle )) / L ;
rotation [ 2 ][ 0 ] = ( vector [ 0 ] * vector [ 2 ] * ( 1 - Cosine ( angle )) - vector [ 1 ] * SquareRoot ( L ) * Sine ( angle )) / L ;
rotation [ 2 ][ 1 ] = ( vector [ 1 ] * vector [ 2 ] * ( 1 - Cosine ( angle )) + vector [ 0 ] * SquareRoot ( L ) * Sine ( angle )) / L ;
rotation [ 2 ][ 2 ] = ( w2 + ( u2 + v2 ) * Cosine ( angle )) / L ;
rotation [ 2 ][ 3 ] = (( point [ 2 ] * ( u2 + v2 ) - vector [ 2 ] * ( point [ 0 ] * vector [ 0 ] + point [ 1 ] * vector [ 1 ])) * ( 1 - Cosine ( angle )) + ( point [ 0 ] * vector [ 1 ] - point [ 1 ] * vector [ 0 ]) * SquareRoot ( L ) * Sine ( angle )) / L ;
rotation [ 3 ][ 0 ] = 0.0 ;
rotation [ 3 ][ 1 ] = 0.0 ;
rotation [ 3 ][ 2 ] = 0.0 ;
rotation [ 3 ][ 3 ] = 1.0 ;
}
stock vec_rotate ( Float : v [ 3 ], Float : k [ 3 ], Float : theta , Float : rotated [ 3 ])
{
new Float : cos_theta = floatcos ( theta );
new Float : sin_theta = floatsin ( theta );
new Float : crossv [ 3 ], kv_dotproduct = xs_vec_dot ( k , v );
xs_vec_cross ( k , v , crossv )
for(new i ; i < 3 ; i ++)
rotated [ i ] = ( v [ i ] * cos_theta ) + ( crossv [ i ] * sin_theta ) + ( k [ i ] * kv_dotproduct ) * ( 1 - cos_theta );
}
stock rotate_3dvector ( Float : fInput_Vector [ 3 ], Float : fAngleX = 0.0 , Float : fAngleY = 0.0 , Float : fAngleZ = 0.0 , Float : fOutput_Vector [ 3 ])
{
static Float : fMatrix [ 3 ][ 3 ];
fMatrix [ 0 ][ 0 ] = floatcos ( fAngleX , degrees ) * floatcos ( fAngleY , degrees );
fMatrix [ 0 ][ 1 ] = floatcos ( fAngleX , degrees ) * floatsin ( fAngleY , degrees ) * floatsin ( fAngleZ , degrees ) - floatsin ( fAngleX , degrees ) * floatcos ( fAngleZ , degrees );
fMatrix [ 0 ][ 2 ] = floatcos ( fAngleX , degrees ) * floatsin ( fAngleY , degrees ) * floatcos ( fAngleZ , degrees ) + floatsin ( fAngleX , degrees ) * floatsin ( fAngleZ , degrees );
fMatrix [ 1 ][ 0 ] = floatsin ( fAngleX , degrees ) * floatcos ( fAngleY , degrees );
fMatrix [ 1 ][ 1 ] = floatsin ( fAngleX , degrees ) * floatsin ( fAngleY , degrees ) * floatsin ( fAngleZ , degrees ) + floatcos ( fAngleX , degrees ) * floatcos ( fAngleZ , degrees );
fMatrix [ 1 ][ 2 ] = floatsin ( fAngleX , degrees ) * floatsin ( fAngleY , degrees ) * floatcos ( fAngleZ , degrees ) - floatcos ( fAngleX , degrees ) * floatsin ( fAngleZ , degrees );
fMatrix [ 2 ][ 0 ] = - floatsin ( fAngleY , degrees );
fMatrix [ 2 ][ 1 ] = floatcos ( fAngleY , degrees ) * floatsin ( fAngleZ , degrees );
fMatrix [ 2 ][ 2 ] = floatcos ( fAngleY , degrees ) * floatcos ( fAngleZ , degrees );
for(new i = 0 ; i < 3 ; i ++)
{
fOutput_Vector [ i ] = ( fInput_Vector [ 0 ] * fMatrix [ i ][ 0 ]) + ( fInput_Vector [ 1 ] * fMatrix [ i ][ 1 ]) + ( fInput_Vector [ 2 ] * fMatrix [ i ][ 2 ])
}
}
stock MultiplyMatrix ( Float : input [ 3 ], Float : rotation [ 4 ][ 4 ], Float : output [ 3 ])
{
new Float : input2 [ 4 ];
input2 [ 0 ] = input [ 0 ];
input2 [ 1 ] = input [ 1 ];
input2 [ 2 ] = input [ 2 ];
input2 [ 3 ] = 1.0 ;
new Float : output2 [ 4 ];
for(new i = 0 , j ; i < 4 ; i ++)
{
for( j = 0 ; j < 4 ; j ++)
{
output2 [ i ] += rotation [ i ][ j ] * input2 [ j ];
}
}
output [ 0 ] = output2 [ 0 ];
output [ 1 ] = output2 [ 1 ];
output [ 2 ] = output2 [ 2 ];
}
// thanks to exolent
stock get_rotation_matrix (const Float : vec1 [ 3 ], const Float : vec2 [ 3 ], Float : out [ 3 ][ 3 ], Float : xangle ) {
// Start by getting the angle between the normals
new Float : angle = xs_vec_angle ( vec1 , vec1 );
// Create the axis of rotation from these normals
new Float : vecAxis [ 3 ];
xs_vec_cross ( vec1 , vec2 , vecAxis );
xs_vec_normalize ( vecAxis , vecAxis );
// Create our skewed-symmetric matrix
new Float : matrixAxisSkewed [ 3 ][ 3 ];
xs_vec_set ( matrixAxisSkewed [ 0 ], 0.0 , vecAxis [ 2 ], - vecAxis [ 1 ]);
xs_vec_set ( matrixAxisSkewed [ 1 ], - vecAxis [ 2 ], 0.0 , vecAxis [ 0 ]);
xs_vec_set ( matrixAxisSkewed [ 2 ], vecAxis [ 1 ], - vecAxis [ 0 ], 0.0 );
// Create a default identity matrix
new Float : matrixIdentity [ 3 ][ 3 ];
matrixIdentity [ 0 ][ 0 ] = 1.0 ;
matrixIdentity [ 1 ][ 1 ] = 1.0 ;
matrixIdentity [ 2 ][ 2 ] = 1.0 ;
// Multiply skewed matrix by sin(theta)
matrix_scale ( matrixAxisSkewed , 3 , 3 , floatsin ( angle , degrees ), out );
// Add the identity matrix
matrix_add ( out , matrixIdentity , 3 , 3 , out );
// Square the skewed matrix and multiply by (1 - cos(theta))
new Float : matrixPart3 [ 3 ][ 3 ];
matrix_mul ( matrixAxisSkewed , matrixAxisSkewed , 3 , 3 , 3 , matrixPart3 );
matrix_scale ( matrixPart3 , 3 , 3 , ( 1.0 - floatcos ( angle , degrees )), matrixPart3 );
// Add to result
matrix_add ( matrixPart3 , out , 3 , 3 , out );
}
stock matrix_scale (const Float : matrix [][], const sizeA , const sizeB , const Float : scale , Float : result [][]) {
for(new a , b ; a < sizeA ; a ++) {
for( b = 0 ; b < sizeB ; b ++) {
result [ a ][ b ] = matrix [ a ][ b ] * scale ;
}
}
}
stock matrix_add (const Float : matrix1 [][], const Float : matrix2 [][], const sizeA , const sizeB , Float : result [][]) {
for(new a , b ; a < sizeA ; a ++) {
for( b = 0 ; b < sizeB ; b ++) {
result [ a ][ b ] = matrix1 [ a ][ b ] + matrix2 [ a ][ b ];
}
}
}
stock matrix_mul (const Float : matrix1 [][], const Float : matrix2 [][], const sizeA , const sizeB , const sizeC , Float : result [][]) {
for(new a , b , c , d ; a < sizeA ; a ++) {
for( b = 0 ; b < sizeB ; b ++) {
for( c = 0 ; c < sizeC ; c ++) {
result [ b ][ c ] = 0.0 ;
for( d = 0 ; d < sizeB ; d ++) {
result [ b ][ c ] += ( matrix1 [ a ][ b ] * matrix2 [ c ][ d ]);
}
}
}
}
}
stock vec_rotate_by_matrix (const Float : vec [ 3 ], const Float : matrix [ 3 ][ 3 ], Float : out [ 3 ]) {
// Convert vector into a matrix
new Float : vec2matrix [ 3 ][ 1 ];
vec2matrix [ 0 ][ 0 ] = vec [ 0 ];
vec2matrix [ 1 ][ 0 ] = vec [ 1 ];
vec2matrix [ 2 ][ 0 ] = vec [ 2 ];
// Multiply the rotation matrix with the vector
new Float : matrixOut [ 3 ][ 1 ];
matrix_mul ( matrix , vec2matrix , 3 , 3 , 1 , matrixOut );
// Convert the output matrix to the vector again
out [ 0 ] = matrixOut [ 0 ][ 0 ];
out [ 1 ] = matrixOut [ 1 ][ 0 ];
out [ 2 ] = matrixOut [ 2 ][ 0 ];
}
stock fm_draw_line ( id , Float : x1 , Float : y1 , Float : z1 , Float : x2 , Float : y2 , Float : z2 , g_iColor [ 3 ])
{
message_begin ( id ? MSG_ONE_UNRELIABLE : MSG_BROADCAST , SVC_TEMPENTITY , _ , id ? id : 0 )
write_byte ( TE_BEAMPOINTS )
write_coord ( floatround ( x1 ))
write_coord ( floatround ( y1 ))
write_coord ( floatround ( z1 ))
write_coord ( floatround ( x2 ))
write_coord ( floatround ( y2 ))
write_coord ( floatround ( z2 ))
write_short ( g_iTrailSprite )
write_byte ( 1 ) // frame
write_byte ( 10 ) // framestart
write_byte ( 10 ) // life
write_byte ( 30 )
write_byte ( 0 )
write_byte ( g_iColor [ 0 ])
write_byte ( g_iColor [ 1 ])
write_byte ( g_iColor [ 2 ])
write_byte ( 200 )
write_byte ( 0 )
message_end ()
}
__________________
Last edited by Natsheh; 11-06-2021 at 18:55 .