2018-07-03 17:36:04 +00:00
/*
* Irresistible Gaming ( c ) 2018
* Developed by Lorenc Pekaj
* Module : cannon . inc
* Purpose : orbital cannon implementation for gang facilities
*/
#if !defined MAX_FACILITIES
#error "This module requires facility module!"
#endif
/* ** Includes ** */
#include < YSI\y_hooks >
#include < mapandreas >
/* ** Definitions ** */
#define ORBITAL_CANNON_TICK ( 100 )
/* ** Variables ** */
enum E_ORBITAL_CANNON_DATA
{
Float : E_POS [ 3 ], Float : E_ZOOM , E_TIMER ,
E_FIRE_TICK , E_COOL_DOWN
};
new
g_orbitalCannonData [ MAX_FACILITIES ] [ E_ORBITAL_CANNON_DATA ],
p_usingOrbitalCannon [ MAX_PLAYERS ] = { - 1 , ... },
Text : g_orbitalAimTD = Text : INVALID_TEXT_DRAW ,
Text3D : g_orbitalPlayerLabels [ MAX_FACILITIES ] [ MAX_PLAYERS ]
;
/* ** Hooks ** */
hook OnScriptInit ( )
{
// start map andreas
MapAndreas_Init ( MAP_ANDREAS_MODE_MINIMAL );
// textdraw
g_orbitalAimTD = TextDrawCreate ( 305.000000 , 205.000000 , " + " );
TextDrawBackgroundColor ( g_orbitalAimTD , 0 );
TextDrawFont ( g_orbitalAimTD , 2 );
TextDrawLetterSize ( g_orbitalAimTD , 1.000000 , 4.000000 );
TextDrawColor ( g_orbitalAimTD , - 16777152 );
TextDrawSetOutline ( g_orbitalAimTD , 1 );
TextDrawSetProportional ( g_orbitalAimTD , 1 );
// starting data
for ( new facilityid = 0 ; facilityid < sizeof ( g_orbitalCannonData ); facilityid ++ ) {
g_orbitalCannonData [ facilityid ] [ E_TIMER ] = - 1 ;
for ( new i = 0 ; i < sizeof ( g_orbitalPlayerLabels [ ] ); i ++ ) {
g_orbitalPlayerLabels [ facilityid ] [ i ] = Text3D : INVALID_3DTEXT_ID ;
}
}
return 1 ;
}
hook SetPlayerRandomSpawn ( playerid )
{
if ( GetPVarType ( playerid , " left_cannon " ) != PLAYER_VARTYPE_NONE )
{
new facilityid = GetPVarInt ( playerid , " left_cannon " );
new int_type = g_gangFacilities [ facilityid ] [ E_INTERIOR_TYPE ];
// place in facility
pauseToLoad ( playerid );
SetPVarInt ( playerid , " in_facility " , facilityid );
UpdatePlayerEntranceExitTick ( playerid );
SetPlayerPos ( playerid , g_gangFacilityInterior [ int_type ] [ E_CANNON_POS ] [ 0 ], g_gangFacilityInterior [ int_type ] [ E_CANNON_POS ] [ 1 ], g_gangFacilityInterior [ int_type ] [ E_CANNON_POS ] [ 2 ] );
SetPlayerVirtualWorld ( playerid , g_gangFacilities [ facilityid ] [ E_WORLD ] );
SetPlayerInterior ( playerid , 0 );
// set camera
DeletePVar ( playerid , " left_cannon " );
SetCameraBehindPlayer ( playerid );
return Y_HOOKS_BREAK_RETURN_1 ;
}
return 1 ;
}
hook OnPlayerDisconnect ( playerid , reason )
{
ClosePlayerOrbitalCannon ( playerid );
return 1 ;
}
2018-07-06 00:01:41 +00:00
#if defined AC_INCLUDED
hook OnPlayerDeathEx ( playerid , killerid , reason , Float : damage , bodypart )
#else
hook OnPlayerDeath ( playerid , killerid , reason )
#endif
{
ClosePlayerOrbitalCannon ( playerid );
return 1 ;
}
2018-07-03 17:36:04 +00:00
/* ** Callbacks ** */
function OnPlayerOrbitalCannonUpdate ( facilityid , playerid )
{
new Float : current_pos [ 3 ];
new Float : move_unit = 10.0 ;
new keys , ud , lr ;
GetPlayerKeys ( playerid , keys , ud , lr );
// store local positions
current_pos [ 0 ] = g_orbitalCannonData [ facilityid ] [ E_POS ] [ 0 ];
current_pos [ 1 ] = g_orbitalCannonData [ facilityid ] [ E_POS ] [ 1 ];
MapAndreas_FindZ_For2DCoord ( current_pos [ 0 ], current_pos [ 1 ], current_pos [ 2 ] );
// close
2018-07-06 00:01:41 +00:00
if ( ( keys & KEY_CROUCH ) || IsPlayerJailed ( playerid ) || IsPlayerAFK ( playerid ) || ( GetPlayerCash ( playerid ) < 250000 && ! g_orbitalCannonData [ facilityid ] [ E_COOL_DOWN ] ) )
2018-07-03 17:36:04 +00:00
{
SetPVarInt ( playerid , " left_cannon " , facilityid );
2018-07-06 00:01:41 +00:00
HidePlayerHelpDialog ( playerid );
if ( IsPlayerMovieMode ( playerid ) ) cmd_moviemode ( playerid , " " );
2018-07-03 17:36:04 +00:00
ClosePlayerOrbitalCannon ( playerid );
return TogglePlayerSpectating ( playerid , 0 );
}
// fire ammo
if ( ( keys & KEY_SPRINT ) && ! g_orbitalCannonData [ facilityid ] [ E_COOL_DOWN ] )
{
// add tick (ms) for countdown
g_orbitalCannonData [ facilityid ] [ E_FIRE_TICK ] += ORBITAL_CANNON_TICK ;
// just pressed fire? move camera
if ( g_orbitalCannonData [ facilityid ] [ E_FIRE_TICK ] == ORBITAL_CANNON_TICK ) {
// smoothly move camera
InterpolateCameraPos (
playerid ,
g_orbitalCannonData [ facilityid ] [ E_POS ] [ 0 ], g_orbitalCannonData [ facilityid ] [ E_POS ] [ 1 ],
current_pos [ 2 ] + g_orbitalCannonData [ facilityid ] [ E_ZOOM ],
current_pos [ 0 ], current_pos [ 1 ], current_pos [ 2 ] + g_orbitalCannonData [ facilityid ] [ E_ZOOM ] + 50.0 ,
5000
);
InterpolateCameraLookAt (
playerid ,
g_orbitalCannonData [ facilityid ] [ E_POS ] [ 0 ], g_orbitalCannonData [ facilityid ] [ E_POS ] [ 1 ], current_pos [ 2 ],
current_pos [ 0 ], current_pos [ 1 ], current_pos [ 2 ],
5000
);
}
// alert
if ( g_orbitalCannonData [ facilityid ] [ E_FIRE_TICK ] % 1000 == 0 )
{
if ( g_orbitalCannonData [ facilityid ] [ E_FIRE_TICK ] > 3000 )
{
g_orbitalCannonData [ facilityid ] [ E_FIRE_TICK ] = 0 ;
g_orbitalCannonData [ facilityid ] [ E_COOL_DOWN ] = ORBITAL_CANNON_TICK * 20 ;
new rocket = CreateDynamicObject ( 3786 , current_pos [ 0 ], current_pos [ 1 ], current_pos [ 2 ] + g_orbitalCannonData [ facilityid ] [ E_ZOOM ], 5.0 , - 90.0 , 0.0 );
new move_speed = MoveDynamicObject ( rocket , current_pos [ 0 ], current_pos [ 1 ], current_pos [ 2 ], 100.0 );
Streamer_Update ( playerid , STREAMER_TYPE_OBJECT );
GivePlayerCash ( playerid , - 250000 );
PlayerPlaySound ( playerid , 1057 , 0.0 , 0.0 , 0.0 );
GameTextForPlayer ( playerid , " ~g~FIRED! " , 2000 , 3 );
SendServerMessage ( playerid , " You have launched an orbital cannon for " COL_GOLD " $ 250,000 " COL_WHITE " , you have %s left. " , number_format ( GetPlayerCash ( playerid ) ) );
return SetTimerEx ( " OnPlayerFireOrbitalCannon " , move_speed , false , " ddfff " , playerid , rocket , current_pos [ 0 ], current_pos [ 1 ], current_pos [ 2 ] );
}
else
{
g_orbitalCannonData [ facilityid ] [ E_ZOOM ] += 2.0 ;
GameTextForPlayer ( playerid , sprintf ( " ~r~%d " , g_orbitalCannonData [ facilityid ] [ E_FIRE_TICK ] / 1000 ), 2000 , 3 );
PlayerPlaySound ( playerid , 1056 , 0.0 , 0.0 , 0.0 );
}
}
}
else
{
g_orbitalCannonData [ facilityid ] [ E_FIRE_TICK ] = 0 ;
}
// deduct cooldown
if ( g_orbitalCannonData [ facilityid ] [ E_COOL_DOWN ] && ( g_orbitalCannonData [ facilityid ] [ E_COOL_DOWN ] -= ORBITAL_CANNON_TICK ) <= 0 )
g_orbitalCannonData [ facilityid ] [ E_COOL_DOWN ] = 0 ;
// begin movement
if ( ! g_orbitalCannonData [ facilityid ] [ E_FIRE_TICK ] )
{
// zoom in
if ( g_orbitalCannonData [ facilityid ] [ E_ZOOM ] > 75.0 ) move_unit = g_orbitalCannonData [ facilityid ] [ E_ZOOM ] / 7.5 ;
else if ( g_orbitalCannonData [ facilityid ] [ E_ZOOM ] <= 20.0 ) move_unit = 5.0 ;
// move camera
if ( ud == KEY_UP ) current_pos [ 1 ] += move_unit ;
else if ( ud == KEY_DOWN ) current_pos [ 1 ] -= move_unit ;
if ( lr == KEY_LEFT ) current_pos [ 0 ] -= move_unit ;
else if ( lr == KEY_RIGHT ) current_pos [ 0 ] += move_unit ;
// zoom in
if ( keys & KEY_FIRE ) {
if ( ( g_orbitalCannonData [ facilityid ] [ E_ZOOM ] -= move_unit ) < 20.0 ) {
g_orbitalCannonData [ facilityid ] [ E_ZOOM ] = 20.0 ;
}
}
else if ( keys & KEY_AIM ) {
if ( ( g_orbitalCannonData [ facilityid ] [ E_ZOOM ] += move_unit ) > 300.0 ) {
g_orbitalCannonData [ facilityid ] [ E_ZOOM ] = 300.0 ;
}
}
// smoothly move camera
InterpolateCameraPos (
playerid ,
g_orbitalCannonData [ facilityid ] [ E_POS ] [ 0 ], g_orbitalCannonData [ facilityid ] [ E_POS ] [ 1 ], g_orbitalCannonData [ facilityid ] [ E_POS ] [ 2 ] + g_orbitalCannonData [ facilityid ] [ E_ZOOM ],
current_pos [ 0 ], current_pos [ 1 ], current_pos [ 2 ] + g_orbitalCannonData [ facilityid ] [ E_ZOOM ],
150
);
InterpolateCameraLookAt (
playerid ,
g_orbitalCannonData [ facilityid ] [ E_POS ] [ 0 ], g_orbitalCannonData [ facilityid ] [ E_POS ] [ 1 ], g_orbitalCannonData [ facilityid ] [ E_POS ] [ 2 ],
current_pos [ 0 ], current_pos [ 1 ], current_pos [ 2 ],
150
);
}
// update
g_orbitalCannonData [ facilityid ] [ E_POS ] = current_pos ;
return 1 ;
}
function OnPlayerFireOrbitalCannon ( playerid , rocketid , Float : X , Float : Y , Float : Z )
{
new Float : player_X , Float : player_Y , Float : player_Z ;
// destroy the rocket after it is moved
DestroyDynamicObject ( rocketid );
// kill everyone in that area
foreach ( new i : Player ) if ( GetPlayerGang ( i ) != GetPlayerGang ( playerid ) && GetPlayerVirtualWorld ( i ) == 0 && GetPlayerInterior ( i ) == 0 && ! IsPlayerJailed ( i ) && ! IsPlayerAdminOnDuty ( i ) && ! IsPlayerSpawnProtected ( i ) )
{
new
player_state = GetPlayerState ( i );
if ( GetPlayerPos ( i , player_X , player_Y , player_Z ) && player_Z >= Z && player_state != PLAYER_STATE_WASTED && player_state != PLAYER_STATE_SPECTATING )
{
new
Float : distance_squared = VectorSize ( player_X - X , player_Y - Y , 0.0 );
if ( distance_squared < 30.0 )
{
SendClientMessageToAllFormatted ( - 1 , " " COL_ORANGE " [ORBITAL CANNON] " COL_WHITE " %s(%d) got rekt by %s(%d)'s orbital cannon. " , ReturnPlayerName ( i ), i , ReturnPlayerName ( playerid ), playerid );
ForcePlayerKill ( i , playerid , 51 );
CreateExplosion ( player_X , player_Y , player_Z , 0 , 10.0 );
continue ;
}
}
}
// create explosion
CreateExplosion ( X , Y , Z , 6 , 10.0 );
return 1 ;
}
/* ** Functions ** */
stock StartPlayerOrbitalCannon ( playerid , facilityid )
{
if ( g_orbitalCannonData [ facilityid ] [ E_TIMER ] != - 1 )
return 0 ;
// player
SetPlayerInterior ( playerid , 0 );
SetPlayerVirtualWorld ( playerid , 0 );
TogglePlayerSpectating ( playerid , 1 );
TextDrawShowForPlayer ( playerid , g_orbitalAimTD );
ShowPlayerHelpDialog ( playerid , 0 , " ~y~Arrows~w~ - Move camera~n~~y~~k~~PED_FIREWEAPON~~w~ - Zoom in~n~~y~~k~~PED_LOCK_TARGET~~w~ - Zoom out~n~~y~~k~~PED_SPRINT~~w~ - Fire cannon ~g~( $ 250,000)~n~~y~~k~~PED_DUCK~~w~ - Cancel " );
p_usingOrbitalCannon [ playerid ] = facilityid ;
if ( ! IsPlayerMovieMode ( playerid ) ) cmd_moviemode ( playerid , " " );
// destroy labels (created on stream out/in anyway)
for ( new i = 0 ; i < sizeof ( g_orbitalPlayerLabels [ ] ); i ++ ) {
DestroyDynamic3DTextLabel ( g_orbitalPlayerLabels [ facilityid ] [ i ] );
g_orbitalPlayerLabels [ facilityid ] [ i ] = Text3D : INVALID_3DTEXT_ID ;
}
// set cannon position
g_orbitalCannonData [ facilityid ] [ E_POS ] [ 0 ] = g_gangFacilities [ facilityid ] [ E_X ];
g_orbitalCannonData [ facilityid ] [ E_POS ] [ 1 ] = g_gangFacilities [ facilityid ] [ E_Y ];
g_orbitalCannonData [ facilityid ] [ E_POS ] [ 2 ] = g_gangFacilities [ facilityid ] [ E_Z ];
// set zoom of camera
g_orbitalCannonData [ facilityid ] [ E_POS ] [ 2 ] += ( g_orbitalCannonData [ facilityid ] [ E_ZOOM ] += 100.0 );
g_orbitalCannonData [ facilityid ] [ E_TIMER ] = SetTimerEx ( " OnPlayerOrbitalCannonUpdate " , ORBITAL_CANNON_TICK , true , " dd " , facilityid , playerid );
return 1 ;
}
hook OnPlayerStreamIn ( playerid , forplayerid )
{
if ( ! IsPlayerNPC ( playerid ) && IsPlayerUsingOrbitalCannon ( forplayerid ) )
{
new
facilityid = p_usingOrbitalCannon [ forplayerid ];
if ( 0 <= facilityid < sizeof ( g_orbitalCannonData ) )
{
if ( ! IsValidDynamic3DTextLabel ( g_orbitalPlayerLabels [ facilityid ] [ playerid ] ) )
{
g_orbitalPlayerLabels [ facilityid ] [ playerid ] = CreateDynamic3DTextLabel (
sprintf ( " %s(%d) " , ReturnPlayerName ( playerid ), playerid ),
setAlpha ( GetPlayerColor ( playerid ), 0xFF ),
0.0 , 0.0 , 0.0 , 300.0 ,
. attachedplayer = playerid ,
. testlos = 0 ,
. playerid = forplayerid ,
. streamdistance = 300.0
);
}
}
}
return 1 ;
}
hook OnPlayerStreamOut ( playerid , forplayerid )
{
if ( ! IsPlayerNPC ( playerid ) && IsPlayerUsingOrbitalCannon ( forplayerid ) )
{
new
facilityid = p_usingOrbitalCannon [ forplayerid ];
if ( 0 <= facilityid < sizeof ( g_orbitalCannonData ) )
{
if ( IsValidDynamic3DTextLabel ( g_orbitalPlayerLabels [ facilityid ] [ playerid ] ) )
{
DestroyDynamic3DTextLabel ( g_orbitalPlayerLabels [ facilityid ] [ playerid ] );
g_orbitalPlayerLabels [ facilityid ] [ playerid ] = Text3D : INVALID_3DTEXT_ID ;
}
}
}
return 1 ;
}
stock ClosePlayerOrbitalCannon ( playerid ) {
new
facilityid = p_usingOrbitalCannon [ playerid ];
// remove user
p_usingOrbitalCannon [ playerid ] = - 1 ;
TextDrawHideForPlayer ( playerid , g_orbitalAimTD );
// reset facility portion
if ( 0 <= facilityid < sizeof ( g_orbitalCannonData ) )
{
// remove label associated
for ( new i = 0 ; i < sizeof ( g_orbitalPlayerLabels [ ] ); i ++ ) {
DestroyDynamic3DTextLabel ( g_orbitalPlayerLabels [ facilityid ] [ i ] );
g_orbitalPlayerLabels [ facilityid ] [ i ] = Text3D : INVALID_3DTEXT_ID ;
}
// kill timer
KillTimer ( g_orbitalCannonData [ facilityid ] [ E_TIMER ] );
g_orbitalCannonData [ facilityid ] [ E_TIMER ] = - 1 ;
}
return 1 ;
}
stock IsPlayerUsingOrbitalCannon ( playerid ) {
return p_usingOrbitalCannon [ playerid ] != - 1 ;
}