s1-scripts-dev/raw/maps/mp/_dynamic_events.gsc
2025-05-21 16:23:17 +02:00

338 lines
9.7 KiB
Plaintext

#include common_scripts\utility;
#include maps\mp\gametypes\_hud_util;
#include maps\mp\_utility;
DEFAULT_START_PERCENTAGE = .5;
SD_WAIT_TIME = 10;
/*
=============
///ScriptDocBegin
"Name: DynamicEvent( dynamicEventStartFunc, dynamicEventResetFunc )"
"Summary: A wrapper for handling global Dynamic event functions. The function handles the timing and notifies the level: "dynamic_event_starting" when it's time. Optionally you can pass in a function that is called at the appropriate time as well.
"Module: Dynamic Event
"CallOn: level
"OptionalArg: dynamicEventStartFunc: The function that will play at the start of the dynamic event
"OptionalArg: dynamicEventResetFunc: The function that will be called to reset the event. Dev Only.
"Example: level thread DynamicEvent( ::dynamicEventStartFunc )
"SPMP: multiplayer"
///ScriptDocEnd
=============
*/
DynamicEvent( dynamicEventStartFunc, dynamicEventResetFunc, dynamicEventEndFunc )
{
if ( getdvarint( "r_reflectionProbeGenerate" ) )//in case maps need to call the dynamic event before load for createfx
return;
if ( IsDefined( level.dynamicEventsType ) )
{
if ( level.dynamicEventsType == 1 ) // Disabled (Before)
return;
if ( level.dynamicEventsType == 2 ) // Disabled (After)
{
if( isDefined( dynamicEventEndFunc ) )
level [[dynamicEventEndFunc]]();
return;
}
}
SetDvarIfUninitialized( "scr_dynamic_event_state", "on"); //options are: on, off, and endstate
if( getdvar( "scr_dynamic_event_state", "on" ) == "off" )
return;
else if( getdvar( "scr_dynamic_event_state", "on" ) == "endstate" )
{
if( isDefined( dynamicEventEndFunc ) )
level [[dynamicEventEndFunc]]();
return;
}
/#
SetDvarIfUninitialized( "scr_dynamic_event_start_perc", DEFAULT_START_PERCENTAGE);
SetDvarIfUninitialized( "scr_dynamic_event_start_now", 0);
#/
if( !isDefined( level.DynamicEvent ) )
level.DynamicEvent = [];
//round based gamemodes
if( level.gametype == "sd" || level.gametype == "sr" )
{
level thread handle_sd_dynamicEvent( dynamicEventStartFunc, dynamicEventEndFunc );
}
/* Removing score check. Dynamic events need to be time based only.
//do score check
else if( level.gametype == "war" || level.gametype == "conf" || level.gametype == "hp" || level.gametype == "dm" )
{
level thread handle_dynamicEvent( dynamicEventStartFunc, dynamicEventResetFunc );
}
*/
//don't do score check
else //ctf, dom, infect, twar
{
level thread handle_dynamicEvent( dynamicEventStartFunc, dynamicEventResetFunc, false );
}
level thread logDynamicEventStartTime();
}
logDynamicEventStartTime()
{
level endon( "game_ended" );
level waittill( "dynamic_event_starting" );
currentDeciSeconds = getTimePassedDeciSecondsIncludingRounds();
setMatchData( "dynamicEventTimeDeciSecondsFromMatchStart", clampToShort( currentDeciSeconds) );
}
handle_sd_dynamicEvent( dynamicEventStartFunc, dynamicEventEndFunc )
{
if( !isDefined( game["dynamicEvent_isInOvertime"] ) )
game["dynamicEvent_isInOvertime"] = false;
if( !isDefined( game["dynamicEvent_hasSwitchedSides"] ) )
game["dynamicEvent_hasSwitchedSides"] = false;
if( !isDefined( game["dynamicEvent_Overtime"] ) )
game["dynamicEvent_Overtime"] = false;
if( !isDefined( game["dynamicEvent_sd_round_counter"] ) )
game["dynamicEvent_sd_round_counter"] = 0;
else
game["dynamicEvent_sd_round_counter"]++;
/# level thread debug_watch_dynamicEvent_start_now( dynamicEventStartFunc );#/
//overtime reset
if( !game["dynamicEvent_isInOvertime"] && game["dynamicEvent_Overtime"] )
{
game["dynamicEvent_sd_round_counter"] = 0;
game["dynamicEvent_isInOvertime"] = true;
game["dynamicEvent_hasSwitchedSides"] = false;
}
//halftime switch sides reset
if( isDefined( game["switchedsides"] ) && game["switchedsides"] && !game["dynamicEvent_hasSwitchedSides"] && !game["dynamicEvent_isInOvertime"] )
{
game["dynamicEvent_sd_round_counter"] = 0;
game["dynamicEvent_hasSwitchedSides"] = true;
}
//do event
else if( game["dynamicEvent_sd_round_counter"] == 1 )
{
wait( SD_WAIT_TIME );
level notify( "dynamic_event_starting" );
if( isDefined( dynamicEventStartFunc ) && isDefined( dynamicEventEndFunc ) )
level [[dynamicEventStartFunc]]();
}
//do end
else if( game["dynamicEvent_sd_round_counter"] > 1 )
{
if( isDefined( dynamicEventStartFunc ) && isDefined( dynamicEventEndFunc ) )
level [[dynamicEventEndFunc]]();
}
}
debug_watch_dynamicEvent_start_now( dynamicEventStartFunc )
{
level endon( "game_ended" );
level notify( "waching_dynamicevent_dvar" );
level endon( "waching_dynamicevent_dvar" );
if( GetDvarInt( "scr_dynamic_event_start_now" ) == 1 )
{
setDvar( "scr_dynamic_event_start_now", 0 );
}
while( true )
{
if( GetDvarInt( "scr_dynamic_event_start_now" ) == 1 && game["dynamicEvent_sd_round_counter"] == 0 )
{
level notify( "dynamic_event_starting" );
if( isDefined( dynamicEventStartFunc ) )
level [[dynamicEventStartFunc]]();
game["dynamicEvent_sd_round_counter"] = 1;
while( GetDvarInt( "scr_dynamic_event_start_now", 1 ) == 1 )
{
wait( 1 );
}
}
wait( 1 );
}
}
handle_dynamicEvent( dynamicEventStartFunc, dynamicEventResetFunc, doScoreCheck )
{
time_limit = getDynamicEventTimeLimit();
start_time = getDynamicEventStartTime();
score = undefined;
score_limit = getScoreLimit();
if( !isDefined( doScoreCheck ) )
doScoreCheck = true;
while( time_limit > start_time && ( !doScoreCheck || ( !isDefined( score ) || score <= score_limit*level.DynamicEvent["start_percent"] ) ) )
{
/#
start_percent = GetDvarfloat( "scr_dynamic_event_start_perc", level.DynamicEvent["start_percent"] );
if( start_percent != level.DynamicEvent["start_percent"] )
{
setDynamicEventStartPercent( start_percent );
start_time = getDynamicEventStartTime();
}
if( GetDvarInt( "scr_dynamic_event_start_now" ) == 1 )
time_limit = start_time;
#/
wait( 1 );
maps\mp\gametypes\_hostmigration::waitTillHostMigrationDone();
time_limit = time_limit - 1;
score = GetDynamicEventHighestScore();
}
level notify( "dynamic_event_starting" );
if( isDefined( dynamicEventStartFunc ) )
level [[dynamicEventStartFunc]]();
/#
while ( IsDefined(dynamicEventResetFunc) )
{
SetDvar("scr_dynamic_event_start_now", 0);
while( !GetDvarInt("scr_dynamic_event_start_now", 0) )
waitframe();
level notify( "dynamic_event_reset" );
level [[dynamicEventResetFunc]]();
SetDvar("scr_dynamic_event_start_now", 0);
while( !GetDvarInt("scr_dynamic_event_start_now", 0) )
waitframe();
level notify( "dynamic_event_starting" );
if( isDefined( dynamicEventStartFunc ) )
level [[dynamicEventStartFunc]]();
}
#/
}
/*
=============
///ScriptDocBegin
"Name: setDynamicEventStartPercent( percent )"
"Summary: Sets when the dynamic event should start."
"Module: Dynamic Event"
"CallOn: level"
"OptionalArg: percent: The percentage of the total match time to start the event. expecting it to be between 0 and 1. default is .5 (50 percent)."
"Example: level setDynamicEventStartPercent( .5 )"
"SPMP: multiplayer"
///ScriptDocEnd
=============
*/
setDynamicEventStartPercent( percent )
{
if( !isDefined( percent ) )
percent = DEFAULT_START_PERCENTAGE;
if( percent < 0 || percent > 1 )
AssertMsg( "expecting a percent between 0 and 1" );
level.DynamicEvent["start_percent"] = percent;
}
/*
=============
///ScriptDocBegin
"Name: getDynamicEventStartTime()"
"Summary: gets the dynamic event start time. if it isn't set, it will set it."
"Module: Dynamic Event"
"CallOn: level"
"Example: start_time = getDynamicEventStartTime()"
"SPMP: multiplayer"
///ScriptDocEnd
=============
*/
getDynamicEventStartTime()
{
if( !isDefined( level.DynamicEvent["start_percent"] ) )
setDynamicEventStartPercent();
time_limit = getDynamicEventTimeLimit();
start_time = time_limit - ( time_limit * level.DynamicEvent["start_percent"] ); // set the move time to a percentage of the timelimit.
return start_time;
}
/*
=============
///ScriptDocBegin
"Name: GetDynamicEventHighestScore()"
"Summary: gets the highest score of one of the teams if teambased. If not teambased it uses player scores. "
"Module: Dynamic Event"
"CallOn: level"
"Example: start_time = GetDynamicEventHighestScore()"
"SPMP: multiplayer"
///ScriptDocEnd
=============
*/
GetDynamicEventHighestScore()
{
score = undefined;
if( level.teamBased )
{
team = maps\mp\gametypes\_gamescore::getWinningTeam();
if( isDefined( team ) && team == "none" && isDefined( level.teamNameList ) )
score = maps\mp\gametypes\_gamescore::_getTeamScore( level.teamNameList[0] );
else if( isDefined( team ) )
score = maps\mp\gametypes\_gamescore::_getTeamScore( team );
}
else
{
player = maps\mp\gametypes\_gamescore::getHighestScoringPlayer();
if( !isDefined( player ) && isDefined( level.players ) && level.players.size > 0 )
score = maps\mp\gametypes\_gamescore::_getPlayerScore( level.players[0] );
else if( isDefined( player ) )
score = maps\mp\gametypes\_gamescore::_getPlayerScore( player );
}
return score;
}
/*
=============
///ScriptDocBegin
"Name: getDynamicEventTimeLimit()"
"Summary: gets the time limit in seconds for the match, used for the dynamic event timing. If there is infinite time, the time limit for the dynamic event will use 600 secs (10 mins)"
"Module: Dynamic Event"
"CallOn: level"
"Example: time_limit = getDynamicEventTimeLimit()"
"SPMP: multiplayer"
///ScriptDocEnd
=============
*/
getDynamicEventTimeLimit()
{
time_limit = getTimeLimit();
if ( time_limit == 0 )//in case the time is infinite time (private match)
time_limit = 10 * 60; // get the game type timelimit in seconds
else
time_limit = time_limit * 60; // get the game type timelimit in seconds
has_half_time = getHalfTime();
if( isDefined( has_half_time ) && has_half_time )
time_limit = time_limit/2;
return time_limit;
}