406 lines
15 KiB
Plaintext
406 lines
15 KiB
Plaintext
#using scripts\codescripts\struct;
|
|
|
|
#using scripts\shared\callbacks_shared;
|
|
#using scripts\shared\challenges_shared;
|
|
#using scripts\shared\drown;
|
|
#using scripts\shared\scoreevents_shared;
|
|
#using scripts\shared\system_shared;
|
|
#using scripts\shared\util_shared;
|
|
#using scripts\shared\weapons\_weapon_utils;
|
|
|
|
#using scripts\mp\_challenges;
|
|
#using scripts\mp\gametypes\_loadout;
|
|
|
|
|
|
|
|
#using scripts\mp\_util;
|
|
|
|
|
|
|
|
|
|
// for blackjack challenge: kills while using a specialist weapon or ability
|
|
// for blackjack challenge: count of unique specialist weapons or abilities used to kill
|
|
|
|
#namespace blackjack_challenges;
|
|
|
|
function autoexec __init__sytem__() { system::register("blackjack_challenges",&__init__,undefined,undefined); }
|
|
|
|
function __init__()
|
|
{
|
|
callback::on_start_gametype( &start_gametype );
|
|
}
|
|
|
|
function start_gametype()
|
|
{
|
|
if ( !isdefined( level.ChallengesCallbacks ) )
|
|
{
|
|
level.ChallengesCallbacks = [];
|
|
}
|
|
|
|
waittillframeend;
|
|
|
|
if ( challenges::canProcessChallenges() )
|
|
{
|
|
challenges::registerChallengesCallback( "playerKilled",&challenge_kills );
|
|
challenges::registerChallengesCallback( "roundEnd",&challenge_round_ended );
|
|
challenges::registerChallengesCallback( "gameEnd",&challenge_game_ended );
|
|
scoreevents::register_hero_ability_kill_event( &on_hero_ability_kill );
|
|
}
|
|
|
|
callback::on_connect( &on_player_connect );
|
|
}
|
|
|
|
function on_player_connect()
|
|
{
|
|
player = self;
|
|
if ( challenges::canProcessChallenges() )
|
|
{
|
|
specialistIndex = player GetSpecialistIndex();
|
|
isBlackjack = ( specialistIndex == 9 );
|
|
if ( isBlackjack )
|
|
{
|
|
player thread track_blackjack_consumable();
|
|
|
|
if ( !isdefined( self.pers[ "blackjack_challenge_active" ] ) )
|
|
{
|
|
remaining_time = player ConsumableGet( "blackjack", "awarded" ) - player ConsumableGet( "blackjack", "consumed" );
|
|
|
|
if ( remaining_time > 0 )
|
|
{
|
|
special_card_earned = player get_challenge_stat( "special_card_earned" );
|
|
if ( !special_card_earned )
|
|
{
|
|
player.pers[ "blackjack_challenge_active" ] = true;
|
|
player.pers[ "blackjack_unique_specialist_kills" ] = 0;
|
|
player.pers[ "blackjack_specialist_kills" ] = 0;
|
|
player.pers[ "blackjack_unique_weapon_mask" ] = 0;
|
|
player.pers[ "blackjack_unique_ability_mask" ] = 0;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
function is_challenge_active()
|
|
{
|
|
return ( self.pers[ "blackjack_challenge_active" ] === true );
|
|
}
|
|
|
|
function on_hero_ability_kill( ability, victimAbility )
|
|
{
|
|
player = self;
|
|
|
|
if ( !isdefined( player ) || !isplayer( player ) )
|
|
return;
|
|
|
|
if ( !isdefined( player.isRoulette ) || !player.isRoulette )
|
|
return;
|
|
|
|
if ( player is_challenge_active() )
|
|
{
|
|
player.pers[ "blackjack_specialist_kills" ]++;
|
|
|
|
currentHeroAbilityMask = player.pers[ "blackjack_unique_ability_mask" ];
|
|
heroAbilityMask = get_hero_ability_mask( ability );
|
|
newHeroAbilityMask = heroAbilityMask | currentHeroAbilityMask;
|
|
if ( newHeroAbilityMask != currentHeroAbilityMask )
|
|
{
|
|
player.pers[ "blackjack_unique_specialist_kills" ]++;
|
|
player.pers[ "blackjack_unique_ability_mask" ] = newHeroAbilityMask;
|
|
}
|
|
|
|
player check_blackjack_challenge();
|
|
}
|
|
}
|
|
|
|
/#
|
|
function debug_print_already_earned()
|
|
{
|
|
if ( GetDvarInt( "scr_blackjack_sidebet_debug", 0 ) == 0 )
|
|
return;
|
|
|
|
IPrintLn( "Blackjack Side Bet already earned this game." );
|
|
}
|
|
#/
|
|
|
|
/#
|
|
function debug_print_kill_info()
|
|
{
|
|
if ( GetDvarInt( "scr_blackjack_sidebet_debug", 0 ) == 0 )
|
|
return;
|
|
|
|
player = self;
|
|
IPrintLn( "Blackjack Side Bet kills: " + player.pers[ "blackjack_specialist_kills" ] + " uniques: " + player.pers[ "blackjack_unique_specialist_kills" ] );
|
|
}
|
|
#/
|
|
|
|
/#
|
|
function debug_print_earned()
|
|
{
|
|
if ( GetDvarInt( "scr_blackjack_sidebet_debug", 0 ) == 0 )
|
|
return;
|
|
|
|
IPrintLn( "Blackjack Side Bet earned!!!" );
|
|
}
|
|
#/
|
|
|
|
function check_blackjack_challenge()
|
|
{
|
|
player = self;
|
|
|
|
/# debug_print_kill_info(); #/
|
|
|
|
special_card_earned = player get_challenge_stat( "special_card_earned" );
|
|
if ( special_card_earned )
|
|
{
|
|
/# debug_print_already_earned(); #/
|
|
return;
|
|
}
|
|
|
|
if ( ( player.pers[ "blackjack_specialist_kills" ] >= 4 ) &&
|
|
( player.pers[ "blackjack_unique_specialist_kills" ] >= 2 ) )
|
|
{
|
|
player set_challenge_stat( "special_card_earned", 1 );
|
|
player AddPlayerStat( "blackjack_challenge", 1 );
|
|
|
|
/# debug_print_earned(); #/
|
|
}
|
|
}
|
|
|
|
function challenge_kills( data )
|
|
{
|
|
attackerisThief = data.attackerIsThief;
|
|
attackerIsRoulette = data.attackerIsRoulette;
|
|
attackerIsThiefOrRoulette = attackerisThief || attackerIsRoulette;
|
|
|
|
if ( !attackerIsThiefOrRoulette )
|
|
return;
|
|
|
|
victim = data.victim;
|
|
attacker = data.attacker;
|
|
player = attacker;
|
|
weapon = data.weapon;
|
|
|
|
if ( !isdefined( weapon ) || ( weapon == level.weaponNone ) )
|
|
return;
|
|
|
|
if ( !isdefined( player ) || !isplayer( player ) )
|
|
return;
|
|
|
|
if ( attackerIsThief )
|
|
{
|
|
if ( weapon.isHeroWeapon === true )
|
|
{
|
|
if ( player is_challenge_active() )
|
|
{
|
|
player.pers[ "blackjack_specialist_kills" ]++;
|
|
|
|
currentHeroWeaponMask = player.pers[ "blackjack_unique_weapon_mask" ];
|
|
heroWeaponMask = get_hero_weapon_mask( attacker, weapon );
|
|
newHeroWeaponMask = heroWeaponMask | currentHeroWeaponMask;
|
|
if ( newHeroWeaponMask != currentHeroWeaponMask )
|
|
{
|
|
player.pers[ "blackjack_unique_specialist_kills" ] += 1;
|
|
player.pers[ "blackjack_unique_weapon_mask" ] = newHeroWeaponMask;
|
|
}
|
|
|
|
player check_blackjack_challenge();
|
|
}
|
|
}
|
|
}
|
|
|
|
// ability kills are handled as events fired from score events
|
|
// if ( attackerIsRoulette )
|
|
// {
|
|
// }
|
|
}
|
|
|
|
function get_challenge_stat( stat_name )
|
|
{
|
|
return self GetDStat( "tenthspecialistcontract", stat_name );
|
|
}
|
|
|
|
function set_challenge_stat( stat_name, stat_value )
|
|
{
|
|
return self SetDStat( "tenthspecialistcontract", stat_name, stat_value );
|
|
}
|
|
|
|
function get_hero_weapon_mask( attacker, weapon )
|
|
{
|
|
if ( !isdefined( weapon ) )
|
|
return 0;
|
|
|
|
if ( isdefined( weapon.isHeroWeapon ) && !weapon.isHeroWeapon )
|
|
return 0;
|
|
|
|
switch( weapon.name )
|
|
{
|
|
case "hero_minigun":
|
|
case "hero_minigun_body3":
|
|
return 1; // note: heroWeaponMask needs to stay unique and consistent for function across TUs and FFOTDs
|
|
break;
|
|
case "hero_flamethrower":
|
|
return 1 << 1;
|
|
break;
|
|
case "hero_lightninggun":
|
|
case "hero_lightninggun_arc":
|
|
return 1 << 2;
|
|
break;
|
|
case "hero_chemicalgelgun":
|
|
case "hero_firefly_swarm":
|
|
return 1 << 3;
|
|
break;
|
|
case "hero_pineapplegun":
|
|
case "hero_pineapple_grenade":
|
|
return 1 << 4;
|
|
break;
|
|
case "hero_armblade":
|
|
return 1 << 5;
|
|
break;
|
|
case "hero_bowlauncher":
|
|
case "hero_bowlauncher2":
|
|
case "hero_bowlauncher3":
|
|
case "hero_bowlauncher4":
|
|
return 1 << 6;
|
|
break;
|
|
case "hero_gravityspikes":
|
|
return 1 << 7;
|
|
break;
|
|
case "hero_annihilator":
|
|
return 1 << 8;
|
|
break;
|
|
default:
|
|
return 0;
|
|
}
|
|
}
|
|
|
|
function get_hero_ability_mask( ability )
|
|
{
|
|
if ( !isdefined( ability ) )
|
|
return 0;
|
|
|
|
switch( ability.name )
|
|
{
|
|
case "gadget_clone":
|
|
return 1; // note: heroAbilityMask needs to stay unique and consistent for functions across TUs and FFOTDs
|
|
break;
|
|
case "gadget_heat_wave":
|
|
return 1 << 1;
|
|
break;
|
|
case "gadget_flashback":
|
|
return 1 << 2;
|
|
break;
|
|
case "gadget_resurrect":
|
|
return 1 << 3;
|
|
break;
|
|
case "gadget_armor":
|
|
return 1 << 4;
|
|
break;
|
|
case "gadget_camo":
|
|
return 1 << 5;
|
|
break;
|
|
case "gadget_vision_pulse":
|
|
return 1 << 6;
|
|
break;
|
|
case "gadget_speed_burst":
|
|
return 1 << 7;
|
|
break;
|
|
case "gadget_combat_efficiency":
|
|
return 1 << 8;
|
|
break;
|
|
default:
|
|
return 0;
|
|
}
|
|
}
|
|
|
|
function challenge_game_ended( data )
|
|
{
|
|
if ( !isdefined( data ) )
|
|
return;
|
|
|
|
player = data.player;
|
|
if ( !isdefined( player ) )
|
|
return;
|
|
|
|
if ( !isPlayer( player ) )
|
|
return;
|
|
|
|
if ( player util::is_bot() )
|
|
return;
|
|
|
|
if ( !player is_challenge_active() )
|
|
return;
|
|
|
|
player report_consumable();
|
|
}
|
|
|
|
function challenge_round_ended( data )
|
|
{
|
|
if ( !isdefined( data ) )
|
|
return;
|
|
|
|
player = data.player;
|
|
if ( !isdefined( player ) )
|
|
return;
|
|
|
|
if ( !isPlayer( player ) )
|
|
return;
|
|
|
|
if ( player util::is_bot() )
|
|
return;
|
|
|
|
if ( !player is_challenge_active() )
|
|
return;
|
|
|
|
player report_consumable();
|
|
}
|
|
|
|
function track_blackjack_consumable()
|
|
{
|
|
level endon( "game_ended" );
|
|
self notify( "track_blackjack_consumable_singleton" );
|
|
self endon( "track_blackjack_consumable_singleton" );
|
|
self endon( "disconnect" );
|
|
|
|
player = self;
|
|
|
|
if ( !isdefined( player.last_blackjack_consumable_time ) )
|
|
player.last_blackjack_consumable_time = 0;
|
|
|
|
while ( isdefined( player ) )
|
|
{
|
|
random_wait_time = GetDvarFloat( "mp_blackjack_consumable_wait", 20.0 ) + RandomFloatRange( -5.0, 5.0 );
|
|
wait random_wait_time;
|
|
|
|
player report_consumable();
|
|
}
|
|
}
|
|
|
|
function report_consumable()
|
|
{
|
|
player = self;
|
|
|
|
if ( !isdefined( player ) )
|
|
return;
|
|
|
|
if ( !isdefined( player.timePlayed ) || !isdefined( player.timePlayed["total"] ) )
|
|
return;
|
|
|
|
current_time_played = player.timePlayed["total"];
|
|
|
|
time_to_report = current_time_played - player.last_blackjack_consumable_time;
|
|
|
|
if ( time_to_report > 0 )
|
|
{
|
|
max_time_to_report = player ConsumableGet( "blackjack", "awarded" ) - player ConsumableGet( "blackjack", "consumed" );
|
|
consumable_increment = int( min( time_to_report, max_time_to_report ) );
|
|
if ( consumable_increment > 0 )
|
|
{
|
|
player ConsumableIncrement( "blackjack", "consumed", consumable_increment ); // so we don't go over awarded time
|
|
}
|
|
}
|
|
|
|
player.last_blackjack_consumable_time = current_time_played;
|
|
}
|